패캠 인강/React

React 기초 다지기 (2) - 리액트의 리렌더링(SPA), VirtualDOM

Je-chan 2022. 1. 12. 23:40

[ 리렌더링이란? ]

  바닐라 자바스크립트의 경우 변경되면 Element 를 처음부터 끝까지 다시 그린다. 만약에 내가  하지만, React 의 경우에는 변경된 부분만을 다시 그린다. 이런 점을 SPA (Single Page Application) 의 특징이라고 부른다. 만약, 티스토리 블로그에서 게시글 리스트를 보다 1페이지에서 2페이지로  넘어갔다고 생각해보자. 그러면 렌더링 되는(화면에 보여지는) 게시글 리스트들은 달라지지만 화면에 보이는 전체적인 레이아웃(한 번에 게시글 몇 개만 보여주는 등)이나, 블로그 이름과 같이 달라지지 않는 내용들도 존재할 것이다. 이전에 바닐라 자바스크립트로만 개발을 한 경우라면 이 변하지 않는 골격이나 달라지지 않는 내용들도 모두 다시 한 번 렌더링 해야 했다. 하지만, SPA 는 변하지 않는 골격과 내용들은 모두 그대로 두고, 변화되는 내용만 바꾼다. 이런 것이 SPA 다. 변경된 부분만 다시 그린다는 것.

 

  결과적으로 SPA 의 장점은

  1. 필요부분만 갱신하기에 전체적인 트래픽을 감소한다
  2. 빠른 화면 이동이 가능해진다
  3. 컴포넌트 단위의 개발이 용이해진다. (변화하는 컴포넌트에만 변화를 줄 수 있으므로)
  4. 변경될 때 다른 요소의 배치에 영향을 주지 않고 최적화할 수 있다. (Reflow 등의 문제를 해결하기 용이하다)  

  단점은  

  1. 검색 엔진 최적화가 어렵다. 

 

  예제를 살펴 보면

<!DOCTYPE html>
<html lang="en">
  <body>
    <script
      crossorigin
      src="https://unpkg.com/react@17/umd/react.development.js"
    ></script>
    <script
      crossorigin
      src="https://unpkg.com/react-dom@17/umd/react-dom.development.js"
    ></script>
    <script src=" https://unpkg.com/@babel/standalone/babel.min.js"></script>
    <div id="root"></div>
    <script>
      const rootElement = document.getElementById("root");
      function randomNumber() {
        const number = Math.floor(Math.random() * 10);
        const element = `<button>${number}</button>`;

        rootElement.innerHTML = element;
      }

      setInterval(randomNumber, 1000);
    </script>

 

  이런 코드의 경우 버튼에 탭을 하면 포커스가 맞춰져 있다가, 내용이 바뀌면 포커스가 해제된다. 그 말인즉슨, 버튼을 매번 생성한다는 것을 의미한다. 하지만 위의 코드를 아래와 같이 리액트로 사용해보면 달라진다. 

 

   <script type="text/babel">
      const rootElement = document.getElementById("root");
      function randomNumber() {
        const number = Math.floor(Math.random() * 10);
        const element = <button>{number}</button>;
        ReactDOM.render(element, rootElement);
      }

      setInterval(randomNumber, 1000);
    </script>

 

  리액트로 사용한다면 탭을 눌러 버튼을 포커스 맞추면 내용이 변화된다 하더라도 포커스가 해제되진 않는다. 변경되는 부분만 바뀌기에 버튼이라는 새로운 요소를 만들지 않는 것이다.

 

[ 렌더링 된 엘리먼트 업데이트하기 ]

  공식 문서에서의 설명은 살펴보자. 리액트는 불변객체(immutable)다. 엘리먼트를 생성한 이후에는 해당 엘리먼트 자식이나 속성을 변경할 수 없다. 엘리먼트는 영화의 프레임과 같이 특정 시점의 UI 를 보여준다.

 

  불변 객체부터 설명하면, 말 그대로 변하지 않는 객체라는 의미다. 위에서 우리는 setInterval 을 통해서 button 이라는 엘리먼트를 만들었다. 그러면 이 버튼은 불변 객체로 바뀌지 않다는 것을 의미한다. Math.random 을 통해 만든 값을 엘리먼트에 넣어줬을 뿐이지, 따로 button 을 형성하거나 만들지 않았다는 의미다. 

 

  이 재조정에서 적용되는 알고리즘 중 하나가 리액트의 비교 알로리즘이다. React 는 데이터가 변경되기 전과 후의 엘리먼트의 루트 엘리먼트를 비교한다. 그 엘리먼트의 타입 다른 경우(예를 들어 우리가 만든 엘리먼트는 button 인데 이 button 태그가 div 태그 등 다른 태그로 바뀐 경우) 이전 것을 지우고 새롭게 만들었다. 그러나 타입이 같은 경우 속성(props)을 비교하여 값이 같으면 유지, 값이 다르다면 달라진 내용으로 변경한다. 우리가 number 로 넣어준 내용은 childeren 이라는 props 의 일종이므로 number 가 바뀌는 것이다.

 

  리액트가 기존의 것과 변경된 것들 사이에서 비교를 할 수 있도록 해주는 것이 Virtual DOM 이다. 이전 Virtual DOM 과 지금의 Virtual DOM 을 비교하고 재조정 알고리즘을 통해서 바뀌었다고 결론내린 데이터를 새롭게 렌더링하는 것이다. 이는 계속 DOM 에 접근해서 변경시키는 것이기에 효율적이다. 

 

  

 

 

 

 

'패캠 인강 > React' 카테고리의 다른 글

React 기초 다지기 (1) - JSX 기초  (0) 2022.01.06
[패캠 인강] React 기초 (5)  (0) 2021.08.27
[패캠 인강] React 기초 (4)  (0) 2021.08.23
[패캠 인강] React 기초 (3)  (0) 2021.08.11
[패캠 인강] React 기초 (2)  (0) 2021.08.07