두 가지 모두 React를 최적화 하기 위한 Hook이다.
useCallback
은 메모이제이션 된 함수를 반환
useMemo
는 메모이제이션 된 값을 반환
컴퓨터 프로그램이 동일한 계산을 반복해야 할 때, 이전에 계산한 값을 메모리에 저장함으로써 동일한 계산의 반복 수행을 제거하여 프로그램 실행 속도를 빠르게 하는 기술이다. 동적 계획법의 핵심이 되는 기술이다.
React의 컴포넌트가 리렌더링 될 때 컴포넌트 내에 있는 모든 함수를 재실행 하게 됩니다. 그렇게 되면 똑같은 함수가 다른 메모리를 차지 하기 때문에 최적화에 좋지 않습니다.
useCallback
은 컴포넌트가 리렌더링 되더라도 함수가 의존하고 있는 값이 변하지 않는 이상 리렌더링 될 때 마다 특정함수의 반복생성을 방지하는 hook입니다.
const memoizedCallback = useCallback(
() => {
doSomething(a, b);
},
[a, b],
);
import {useCallback, useState} from 'react'
const Form = () => {
const [row, setRow] = useState(10);
const [cell, setCell] = useState(10);
const [mine, setMine] = useState(20);
const { dispatch } = useContext(TableContext);
const onChangeRow = useCallback((e) => {
setRow(e.target.value);
}, []);
const onChangeCell = useCallback((e) => {
setCell(e.target.value);
}, []);
const onChangeMine = useCallback((e) => {
setMine(e.target.value);
}, []);
const onClickBtn = useCallback(() => {
dispatch(startGame(row, cell, mine));
}, [row, cell, mine]);
}
위와 같이 useCallback의 의존성 배열에 [row, cell, mine]
을 넣으면 의존성 배열의 값이 변해야 함수를 실행합니다.
의존성 배열값을 잘못 입력하면 원하지 않게 실행이 될 수 있으니 주의해야 합니다.
의존성 배열에 빈 배열을 넣게되면 렌더링 후 최초의 한 번만 실행을 합니다.
즉 렌더링이 일어날 때 마다 실행을 하게 됩니다.
state가 의존적이지 않은 함수라면 빈배열을 [ ]
입력하면 됩니다.
useMemo
는 메모이제이션된 값을 반환합니다. 사용방법은 useCallback과 유사하게 사용할 수 있습니다. 함수의 연산량이 많을때 이전 결과값을 재사용 하는 hook입니다.
const memoizedValue = useMemo(() => computeExpensiveValue(a, b), [a, b]);
const lottoNumbers = useMemo(() => getWinNumbers(), []);
위처럼 의존성 배열이 없는 경우 매 렌더링 때마다 새 값을 계산합니다.
의존성 배열을 추가할 경우 해당 값이 업데이트 될 때 실행합니다.