useCallback()
useCallback은 useMemo와 비슷한 Hook입니다. useMemo는 특정 결괏값을 재사용할 때 사용하는 반면, useCallback은 특정 함수를 새로 만들지 않고 재사용하고 싶을 때 사용하는 함수입니다. |
useCallback 사용법
const memoizedCallback = useCallback(function, deps);
useCallback은 첫 번째 인자로 넘어온 함수를, 두 번째 인자로 넘어온 배열 형태의 함수 실행 조건의 값이 변경될 때까지 저장해놓고 재사용할 수 있게 해 줍니다.
예를 들어 리액트 컴포넌트 안에 함수가 선언되어있을 때 이 함수는 해당 컴포넌트가 렌더링 될 때마다 새로운 함수가 생성되는데, useCallback을 사용하면 해당 컴포넌트가 렌더링 되더라도 그 함수가 의존하는 값(deps)들이 바뀌지 않는 한 기존 함수를 재사용할 수 있습니다.
useCallback을 사용하는 이유
컴포넌트가 리렌더링될 때마다, 동일한 함수를 재호출하여, 생성하지 않도록 막기 위해서 사용한다. |
단, 모든 함수에 useCallback을 사용하게 되면 오히려 성능 저하를 발생시킬 수 있다. |
의존성 배열(대부분 useCallback 내부에서 사용하는 정보를 의존성 배열에 추가하지 않으면 최신값을 반영하지 못할 수 있다. |
useCallback이 필요한 경우
1️⃣ 자식 컴포넌트에 함수를 props로 전달할 때
- 부모 컴포넌트가 리렌더링 될때마다 새로운 함수 객체가 생성되면 useMemo 가 설정된 자식 컴포넌트일지라도 불필요하게 재렌더링될 수 있다.
import React, { useState, useCallback } from "react";
const Child = React.memo(({ onClick }) => {
console.log("Child 렌더링!");
return <button onClick={onClick}>클릭</button>;
});
export default function Parent() {
const [count, setCount] = useState(0);
const handleClick = useCallback(() => {
console.log("버튼 클릭!");
}, []);
return (
<div>
<p>Count: {count}</p>
<button onClick={() => setCount(count + 1)}>증가</button>
<Child onClick={handleClick} />
</div>
);
}
하지만 useCallback을 사용하면 handleClick이라는 함수가 재생성되지 않으므로 Child 컴포넌트가 불필요하게 재랜러링되지 않게 된다.
2️⃣ 함수를 useEffect의 의존성으로 넣어야 할 때
- useEffect에서 특정 함수를 의존성으로 포함해야 하는 경우, 함수가 리렌더링될 때마다 새로 생성되면 useEffect가 불필요하게 실행될 수 있다.
import React, { useState, useEffect, useCallback } from "react";
export default function App() {
const [count, setCount] = useState(0);
const logMessage = useCallback(() => {
console.log(`현재 카운트: ${count}`);
}, [count]);
useEffect(() => {
logMessage();
}, [logMessage]); // useCallback을 사용하지 않으면 매번 useEffect 실행됨
return <button onClick={() => setCount(count + 1)}>증가</button>;
}
- 하지만 useCallback을 사용하면 같은 함수 객체를 유지하여 useEffect가 불필요하게 실행되는 것을 방지할 수 있다!
- logMessage가 useCallback으로 감싸져 있어서 count가 변경될 때만 함수가 변경된다.
3️⃣ 이벤트 핸들러가 빈번하게 재생성될 때
- 렌더링이 자주 발생하는 컴포넌트에서 이벤트 핸들러가 자주 생성되는 경우, 성능 최적화에 좋다.
useCallback이 불필요한 경우
1️⃣ 컴포넌트가 자주 리렌더링되지 않는 경우
- useCallback은 함수 객체의 동일성을 유지하는 것일 뿐, 실행 속도를 빠르게 해주는 것은 아니므로, 함수 재생성이 성능 저하를 유발하지 않는다면 굳이 사용할 필요 없다.
2️⃣ props로 함수를 전달하지 않는 경우
- useCallback은 함수 참조 동일성을 유지하는 것이 목적이므로, 컴포넌트 내부에서만 사용하는 함수라면 useCallback을 사용할 필요가 없다.
3️⃣ 불필요하게 사용하면 오히려 성능 저하
- useCallback도 내부적으로 메모이제이션을 수행하므로 메모리 사용량이 증가할 수 있다.
- 함수 생성 비용보다 useCallback 자체의 비용이 더 크다면 오히려 성능이 나빠질 수도 있다.
Hook –useReducer()
: 현재 상태와 업데이트를 위해 필요한 정보를 담은 액션 값을 전달받아 새로운 상태를 반환하는 함수 |
• 장점: 컴포넌트 업데이트 로직을 컴포넌트 외부로 뺄 수 있음 |
• useReducer은 useState의 대체 함수로 다양한 컴포넌트 상황에 따라 상태값을 설 정할 수 있다. |
참고) useState() vs. useReducer()
• useReducer()가 useState() 기반이라고 해서 더 좋은 것은 아니다! |
• 상황에 따라 적절한 hook 을 선택하자 |
• state가 단순하다면 useState()를 사용 |
• state가 복잡하다면 useReducer()를 사용 |
'국비지원 공부 정리 > React' 카테고리의 다른 글
React Style - Sass, Styled-Components, Tailwind (0) | 2025.04.02 |
---|---|
Custom Hooks (0) | 2025.04.01 |
Hooks - 기본 설명, useMemo (0) | 2025.04.01 |
react-hook-form의 사용법 (1) | 2025.04.01 |
react의 Life Cycle, useEffect (0) | 2025.03.31 |