React中useMemo与常规变量声明的技术疑问
React中useMemo与常规变量声明的技术疑问
嘿,这个问题问得特别精准,刚好摸到了React中useMemo和普通变量声明的核心区别,我来给你拆解明白~
首先回答第一个问题:result会不会像isLeapYear一样每次渲染都重新计算?
先看你的代码:
const isLeapYear = year % 4 === 0; // year 是 props const result = useMemo(() => console.log('complex function', isLeapYear), [isLeapYear]);
isLeapYear是在组件函数体内直接声明的变量,所以每次组件渲染时,这行代码都会执行一遍,重新算出isLeapYear的值。- 而
useMemo的逻辑是:只有当依赖数组里的isLeapYear的值和上一次渲染时不一样时,才会重新执行回调函数(也就是你说的“复杂函数”);如果isLeapYear的值没变,哪怕组件重新渲染了,useMemo也会直接返回上一次缓存的结果,不会再跑回调。
举个例子:如果传入的year从2020(闰年,isLeapYear为true)变成2024(也是闰年,isLeapYear还是true),这时候组件会重新渲染,isLeapYear会重新计算,但因为值没变,useMemo的回调不会执行,result还是用的之前缓存的结果。
然后是第二个问题:要不要也用useMemo声明isLeapYear?
这得看isLeapYear的计算复杂度:
- 像你例子里这种简单的取模判断,完全没必要套
useMemo!因为这种计算的性能开销极小,甚至比useMemo本身维护缓存的开销还低,强行用反而会增加不必要的内存消耗,属于画蛇添足。 - 但如果
isLeapYear的计算逻辑很复杂(比如要遍历大量数据、做多层日期校验),那用useMemo缓存它的值就很有意义了——这样每次渲染时不用重复跑复杂计算,同时依赖它的useMemo也能更稳定(不过哪怕isLeapYear没被memo,只要它的值不变,依赖它的useMemo还是不会重新执行,只是isLeapYear自己会多算一遍而已)。
总结一下:
- 简单计算的变量,直接用常规声明就行,没必要上
useMemo; - 复杂计算的变量,用
useMemo缓存能有效减少重复计算的开销; useMemo的触发只看依赖值的变化,和依赖变量本身是否被memo无关。
内容来源于stack exchange
相关产品推荐
相关产品推荐

