이미 계산해본 연산 결과를 기억해두었다가, 동일한 계산을 하였을 때에 다시 계산하지 않고, 기억해두었던 데이터를 반환하는 것
마치, 예전에 풀었던 문제가 똑같이 시험에 나오면, 다시 처음부터 계산하지않고 답만 적는 것 처럼!
useMemo, React.memo를 사용하여 memoization을 해보자
시작 전에, 간단히 useMemo와 React.memo의 차이점을 말하자면
공통점은 ? props가 변하지 않으면 재실행 하지 않고, 이전에 메모해둔 값을 반환한다 (=> 불필요한 연산/렌더링을 하지 않아 성능 개선)
return 값을 가지고 있는 연산 함수인데, 특정 값이 변화할때만 연산을 수행하고 싶다면?
memo하고 싶은 부분을 useMemo()
로 감싸주면 된다
const getAnalysis = () => {
return
}
// 값을 사용할 때 getAnalysis()
const getAnalysis = useMemo(() => {
return
}, [dependency array])
// 값을 사용할 때 getAnalysis
useMemo vs useEffect?
useMemo는 함수가 무거운 경우 렌더링마다 계산하는 것은 처리 시간이 오래 걸리므로 값을 기억해놓고 의존성이 변경되었을 경우에만 다시 계산해주는 기능
useEffect의 경우는 한 번만 호출해도 될 기능들이 렌더링되어 실행되거나, 호출과정에서 렌더링에 영향을 끼칠 수 있는 것을 모아서 따로 처리하기 위한 기능
둘의 가장 큰 차이점은 useEffect는 해당 컴포넌트의 렌더링이 완료된 후에 실행되지만, useMemo는 렌더링 중에 실행되어진다는 것
리액트 공식문서에 의하면 상황에 맞게 적절한 기능을 사용하는 것이 중요하다
// 1) export 할 때 감싸주기
export default React.memo(component);
// 2) 컴포넌트 만들 때 감싸주기
const MyComponent = React.memo((props) => {
return (/*컴포넌트 렌더링 코드*/)}
);
중요한 것
props가 object인 경우 얕은 비교를 하기 때문에, 같은 객체가 들어가더라도 리렌더링이 발생하게 된다.
이를 위해서는 React.memo의 두번째 인자에 areEqual이라는 비교함수를 넣어서, 기존의 props와 새로운 props의 값을 비교해주는 방법을 사용하면 된다.
const MyComponent = (props) => { return (/*컴포넌트 렌더링 코드*/) } const areEqual = (prevProps, nextProps) { /* 전달되는 nextProps가 prevProps와 같다면 true, 같지 않다면 false ex) 예를 들면 */ return prevProps.id === nextProps.id } export default React.memo(MyComponent, areEqual);
언제 쓰면 좋을까?