React useMemo钩子依赖数组警告问题及使用注意事项咨询
问题场景代码
const [getNum, setNum] = useState(1); function generateNum(){ let randomNum = Math.floor(Math.random() * 100 + 1); setNum(randomNum); } const doubleNum = useMemo(()=>{ return doubleTheNum(); }, [getNum]) function doubleTheNum(){ return getNum * 2; }
ESLint警告信息
WARNING in [eslint] src\AppMemo.js Line 51:6: React Hook useMemo has a missing dependency: 'doubleTheNum'. Either include it or remove the dependency array react-hooks/exhaustive-deps webpack compiled with 1 warning
问题原因解析
ESLint的react-hooks/exhaustive-deps规则要求:Hook的依赖数组必须包含所有在Hook回调内部用到的外部变量和函数。
你的代码里,useMemo的回调调用了doubleTheNum函数,这个函数定义在组件内部,每次组件重新渲染都会被重新创建。ESLint检测到回调引用了这个函数,但它没出现在依赖数组里,所以抛出警告。
当你把getNum作为参数传入doubleTheNum后,这个函数不再直接依赖组件作用域里的getNum,此时它要么是useMemo回调内部的局部函数,要么只依赖传入的参数,ESLint就不会再检测到缺失的依赖,自然就没有警告了。
useMemo使用注意事项
- 严格维护依赖数组:必须把回调内部用到的所有外部变量、函数都加入依赖数组,遗漏会导致缓存值过期,出现不符合预期的渲染结果。
- 处理不稳定的函数引用:组件内普通函数每次渲染都会重新创建,直接加进依赖数组会让
useMemo每次都重新计算。可以用useCallback包裹函数来稳定引用,或者把函数逻辑直接写在useMemo回调内部,也可以通过参数传递依赖来避免外部引用。 - 不要滥用useMemo:它是用来缓存复杂计算结果、避免不必要重计算的。如果计算逻辑很简单,没必要用——额外的缓存开销可能比重新计算更大。
- 空依赖数组要谨慎:空数组意味着
useMemo只在组件首次渲染时计算一次,后续无论外部变量怎么变都不会更新,除非你明确需要永久缓存某个值,否则别这么用。
内容的提问来源于stack exchange,提问作者Sahil Nayak
相关产品推荐
相关产品推荐

