본문 바로가기

리액트 React/Hooks

리액트 훅스 Hooks 5: useCallback

반응형

useMemo와 비슷한 useCallback은 메모이제이션된 콜백을 반환하고 렌더링 선능을 최적화해야 할때 사용됩니다. 

 

전편에서 구현한 곱셈 컴포넌트에서 onChange와 onClick 함수를 선언해 주었는데 이러면 컴포넌트가 리렌더링 될때마다 새로 만들어진 함수를 사용하게 됩니다. 

 

Multiply.js
import React, {useMemo, useState} from 'react';

const getMultiply = numbers => {
    console.log("calculating");
    if(numbers.length === 0) return 0;
    const sum = numbers.reduce((a,b)=> a*b);
    return sum;
};

const Multiply = () => {
    const [list, setList] = useState([]);
    const [number, setNumber] = useState('');

    const onChange = e => {
        setNumber(e.target.value);
    };

    const onClick = e => {
        const nextList = list.concat(parseInt(number));
        setList(nextList);
        setNumber('');
    }

    const result = useMemo(() => getMultiply(list), [list]);

    return(
        <div>
            <input value={number} onChange={onChange} />
            <button onClick={onClick}>multiply</button>
            <ul>
                {list.map((value, index)=>(
                    <li key={index}>{value}</li>
                ))}
            </ul>
            <div>
                    <b>result:</b> {result}
            </div>
        </div>
    )
}

export default Multiply;

 

useCallback 적용 후 
import React, { useMemo, useState, useCallback } from "react";

const getMultiply = (numbers) => {
  console.log("calculating");
  if (numbers.length === 0) return 0;
  const sum = numbers.reduce((a, b) => a * b);
  return sum;
};

const Multiply = () => {
  const [list, setList] = useState([]);
  const [number, setNumber] = useState("");

  const onChange = useCallback((e) => {
    setNumber(e.target.value);
  }, []);

  const onClick = useCallback(
    (e) => {
      const nextList = list.concat(parseInt(number));
      setList(nextList);
      setNumber("");
    },
    [number, list]
  );

  const result = useMemo(() => getMultiply(list), [list]);

  return (
    <div>
      <input value={number} onChange={onChange} />
      <button onClick={onClick}>multiply</button>
      <ul>
        {list.map((value, index) => (
          <li key={index}>{value}</li>
        ))}
      </ul>
      <div>
        <b>result:</b> {result}
      </div>
    </div>
  );
};

export default Multiply;

 useCallback의 첫번째 파라미터에는 생성하고 싶은 함수를 넣고, 두번째 파라미터에는 배열을 넣으면 됩니다. 이 배열에 의존하여 어떤 값이 바뀌었을때 함수를 새로 생성해야 하는지 명시해야 합니다.

 

onChange경우에는 기존의 값과 무관하게 설정만 하기 때문에 배열이 비어있어도 되지만 onClick의 경우는 number와 list를 조회하고 nextList를 생성하기 때문에 배열안에 number와 list를 넣어주어야 합니다.

반응형