Studying/React

리액트 공부하기 - 최적화 함수 useMemo(), useCallback(), memo()

creamymood 2025. 5. 14. 16:06

리렌더링이 발생되는 기존 조건 때문에, 

꼭 리렌더링 될 필요 없을 때, 불필요하게 발생되는 비효율적인 순간들이 있다.

규모가 복잡해질 수록, 성능좋고 빠르게 만들기 위해, 최적화 함수!

 


등장 배경은? 바로 함수형이라서 그렇다 ?

 

이게 무슨 말이냐면..

 

함수형 컴포넌트는 함수를 호출해서 화면에 그리는 식.

이런 함수형 컴포넌트에서 상태변경이 일어나면, 그 함수는 더 이상 사용하지 않고 새 상태값으로 함수를 새롭게 호출.

따라서 상태가 변경되면 이전의 기존의 함수는 사라지고, 새 함수로 대체되는. 

재사용 가능 한 것도 새로만들어쓰는 비 효율 발생!

 


그렇다면.. 해결 방법은?

 

따라서 리액트 최적화 함수들은, 이런 생각에서 만들어진 함수들이다 !

 

저장 했다가 재 사용 하자 !


각각 함수를 어떻게 사용하는지 살펴보자.

 

1. useMemo()

 

예를 들어 연산이 복잡하다면, 결과값을 리턴하는데 오래 걸리고 불필요하게 리렌더링 된다면, 그야말로 비효율이 아닐 수 없음..

따라서 useMemo()사용하여, 결과를 저장!

 

const memoizedValue = useMemo(() => {
  return computeExpensiveValue(a, b);
}, [a, b]);

설명:

  • 복잡한 계산 결과를 기억해뒀다가, 의존성 값(a, b)이 바뀔 때만 다시 계산.

언제 사용?

  • 계산량이 큰 함수의 결과값이 렌더링마다 다시 계산되는 걸 막고 싶을 때.

2. useCallback

문법은 useMemo와 동일하나, useMemo는 함수 값을 저장하고, useCallback은 함수 자체를 저장

const handleClick = useCallback(() => {
  console.log('Clicked');
}, []);

설명:

  • 함수 자체를 메모이징해요.
  • 의존성 배열 안의 값이 바뀌지 않으면 같은 함수 객체를 재사용해요.

언제 사용?

  • props로 함수를 자식 컴포넌트에 전달할 때,
더보기

"props로 함수 넘길 때"가 무슨 뜻인가?

 

1. 먼저, props가 뭔지 복습!

React에서 props는 부모 컴포넌트가 자식 컴포넌트에 값을 전달하는 방법이에요.

function Child({ name }) {
  return <p>Hello, {name}</p>;
}

function Parent() {
  return <Child name="Jane" />;
}

여기서 name="Jane"은 Child에게 props로 넘긴 값이에요.

 

그럼 "함수를 props로 넘긴다"는 건?

props로 값뿐만 아니라 함수도 넘길 수 있어요.

function Child({ onClick }) {
  return <button onClick={onClick}>Click me</button>;
}

function Parent() {
  const sayHello = () => {
    alert("Hello!");
  };

  return <Child onClick={sayHello} />;
}
  • 위 코드에서 sayHello는 함수예요.
  • 이 함수를 Child에게 props로 넘겼어요 → onClick={sayHello}
  • Child는 onClick props를 받아서 버튼에 연결했어요.

이게 바로 **"props로 함수 넘기기"**에요!

 

 왜 이게 중요할까?

리액트에서 부모 컴포넌트가 리렌더링되면,
내부에 선언된 함수들도 새로 만들어진 함수처럼 바뀌어요.

그럼 자식 컴포넌트는 이렇게 생각해요:

"어? props로 받은 함수(onClick)가 바뀌었네? 나도 다시 렌더링해야겠다!"

이걸 막기 위해 useCallback으로 함수를 기억해 두는 것이에요:

const sayHello = useCallback(() => {
  alert("Hello!");
}, []);

이렇게 하면 sayHello 함수는 리렌더링될 때마다 새로 안 만들어져서,
자식 컴포넌트는 "props 안 바뀌었네~" 하고 렌더링을 건너뛸 수 있어요.

 간단 요약


props로 함수 넘긴다 부모가 자식에게 함수를 전달해서, 자식이 그 함수를 호출할 수 있게 하는 것
useCallback 쓰는 이유 부모 리렌더링 시 함수가 바뀌는 걸 방지해서 자식이 불필요하게 렌더링되지 않게 하기

참고 개념: "함수도 그냥 이다"

리액트에서 컴포넌트는 props로 무엇이든 전달할 수 있어요.
문자열, 숫자, 객체, 배열뿐만 아니라 함수도 가능해요.

즉, 아래는 모두 props 전달이야:

<Child text="hi" number={3} onClick={someFunction} />
  • text에는 "hi"라는 문자열 값
  • number에는 3이라는 숫자 값
  • onClick에는 someFunction이라는 함수 값

즉! 함수도 그냥 하나의 값이야.
그 값을 자식 컴포넌트가 props로 받아서 사용할 수 있어요.

 

function Child({ onClick }) {
  return <button onClick={onClick}>Click me</button>;
}

 

  • Child 컴포넌트는 onClick이라는 이름의 props를 받아요.
  • 그리고 이 onClick을 <button>에 연결해요.
  • 이 말은 곧: "부모가 준 함수를, 버튼이 눌렸을 때 실행해!"라는 뜻.

 

  • 자식 컴포넌트가 매번 렌더링되는 걸 막고 싶을 때.

3. memo()

const MyComponent = React.memo(function MyComponent(props) {
  return <div>{props.name}</div>;
});

설명:

  • 컴포넌트 전체를 메모이징해요.
  • props가 바뀌지 않으면 리렌더링하지 않음.

언제 사용?

  • 자주 바뀌지 않는 props를 받는 자식 컴포넌트가 있을 때.
  • 부모 컴포넌트가 자주 리렌더링되더라도 자식은 그대로 유지하고 싶을 때.