본문 바로가기

TIL

TIL - 리액트 훅과 가상 DOM의 상호작용

1. 가상 DOM (Virtual DOM)

리액트에서 사용하는 가상 DOM은 렌더링 효율성을 높이기 위해 실제 DOM의 경량화된 사본을 메모리 내에서 유지합니다. 상태나 props가 변경되면 리액트는 새로운 가상 DOM을 생성하고, 이전 가상 DOM과 비교(diffing)하여 변경된 부분만 실제 DOM에 반영(patching)합니다. 이는 전체 DOM을 다시 렌더링하지 않고, 변경된 부분만 업데이트함으로써 성능을 최적화하고, UI 업데이트를 예측 가능하게 만듭니다.

2. useRef

useRef는 리액트 훅으로, DOM 요소나 변경 가능한 값의 참조를 유지하는 데 사용됩니다. 컴포넌트의 전 생애주기 동안 유지되는 ref 객체를 생성합니다. useRef는 DOM 요소에 접근하거나, 상태 변화 없이 변수 값을 유지할 때 유용합니다.

 

function FocusInput() {
  const inputRef = useRef(null);

  useEffect(() => {
    inputRef.current.focus();
  }, []);

  return <input ref={inputRef} placeholder="Focus me!" />;
}

useRef를 사용하여 input 요소에 접근하고, useEffect를 통해 컴포넌트가 렌더링된 후 input에 포커스를 설정합니다.

 

3. useEffect

useEffect는 리액트 훅으로, 컴포넌트가 렌더링된 후에 비동기적으로 실행됩니다. 데이터 페칭, 구독 설정, 이벤트 리스너 설정 등 렌더링 이후에 수행해야 하는 작업에 사용됩니다. useEffect는 비동기적으로 실행되므로, UI 업데이트 성능에 큰 영향을 미치지 않습니다.

function FetchData() {
  const [data, setData] = useState(null);

  useEffect(() => {
    async function fetchData() {
      const response = await fetch('https://api.example.com/data');
      const result = await response.json();
      setData(result);
    }
    fetchData();
  }, []);

  return <div>{data ? JSON.stringify(data) : 'Loading...'}</div>;
}

useEffect는 컴포넌트가 렌더링된 후 데이터를 페칭하고, 상태를 업데이트합니다

4. useLayoutEffect

useLayoutEffect는 리액트 훅으로, 모든 DOM 변경 후, 브라우저가 화면을 그리기 전에 동기적으로 실행됩니다. DOM을 직접 조작하거나, 레이아웃 계산이 필요한 작업에 사용됩니다. useLayoutEffect는 동기적으로 실행되므로, UI 업데이트의 성능에 영향을 줄 수 있습니다.

function MeasureWidth() {
  const divRef = useRef(null);

  useLayoutEffect(() => {
    console.log(divRef.current.offsetWidth);
  });

  return <div ref={divRef}>Measure my width</div>;
}

useLayoutEffect는 컴포넌트가 렌더링된 직후, 브라우저가 화면을 그리기 전에 div 요소의 너비를 측정합니다.

 

요약

리액트의 useRef, useEffect, useLayoutEffect 훅과 가상 DOM은 서로 상호작용하여 효율적인 렌더링과 상태 관리를 가능하게 합니다. 가상 DOM은 변경된 부분만 실제 DOM에 반영하여 성능을 최적화하고, useRef는 DOM 요소나 값의 참조를 유지하며, useEffect는 렌더링 후 비동기 작업을 처리하고, useLayoutEffect는 렌더링 후 동기적으로 DOM 조작을 수행합니다.