什么是useCallback
useCallback 是一个优化渲染性能的hook,useCallback 允许在多次渲染中缓存函数。
为什么需要useCallback
在memo章节中介绍了memo会通过比较prop来决定使用记忆化组件渲染还是执行渲染函数来渲染组件。在某些情况下,需要通过prop将父组件中定义的函数传递给子组件(修改父组件状态的set函数),这时,在父组件的每次渲染时,都会创建新的set函数,子组件的prop都发生了变更,导致memo失效,子组件也会随着父组件的更新而更新。为了不让记忆化组件失效,可以通过useCallback包裹set函数,这样当useCallback的以来数据未发生变化时,返回缓存的函数,这样子组件的prop就不会发生变化,从而跳过子组件的渲染,使用记忆化组件。同样的道理,可以避免Effect等不必要的更新
useCallback的基本使用
useCallback 接收一个函数,一个依赖数组。返回一个记忆化的函数。useCallback的底层通过useMemo来实现的,其基本使用和实现原理如下:
//基本实现
function useCallback(fn, deps) {
const memoFn = useMemo(() => fn, deps);
return memoFn;
}
//基本使用
const MemoComponent = memo(({list, changeList}) => {
return(
<div>
{list.map((item) => (
<div key={item.value}>{item.value}</div>
))}
<button onClick={() => changeList("hello")}>add</button>
</div>
)
})
function App() {
const [list, setList] = useState([]);
//创建缓存函数
const changeList = useCallback((name) => {
setList([...list, {value:name}]);
}, [list]);
return (
<div>
<MemoComponent list={list} changeList={changeList} />
</div>
);
}