javascript - 将详尽的依赖项添加到 useEffect 和 useCallback 会导致无限循环
问题描述
所以我以为我掌握了这些钩子的窍门,但皮棉规则react-hooks/exhaustive-deps
让我绊倒了。
const onScreenChange = useCallback(
(key, value) => {
const newState = Object.assign({}, screenState, { [key]: value });
localStorage.setItem('screens', JSON.stringify(newState));
setScreenState(newState);
},
[]); // screenState
我允许我的应用程序的其余部分通过将其传递给 value 属性来访问它...
return <Provider value={{onScreenChange, ... }}>children</Provider>
然后当路由改变时我从子组件调用这个方法
useEffect(() => {
if (match.path === `/${screenKey}`) {
onScreenChange(screenKey, 'external');
}
}, [onScreenChange, match.path, screenKey]);
上面的代码完全按照我的意愿工作,我看不到这会导致任何错误。然而 eslint 告诉我:
React Hook useCallback has a missing dependency: 'screenState'. Either include it or remove the dependency array
当我添加screenState
到数组中时,只要onScreenChange
调用该方法就会导致无限循环。
很明显为什么现在正在发生循环,但是我该如何阻止它并“遵守规则”呢?
提前感谢您的帮助!
解决方案
来自 eslint 的警告似乎是正确的。onScreenChange
因为如果多次调用该方法,screenState 值将不会正确更新。您必须提供screenState
作为依赖useCallback
const onScreenChange = useCallback(
(key, value) => {
const newState = Object.assign({}, screenState, { [key]: value });
localStorage.setItem('screens', JSON.stringify(newState));
setScreenState(newState);
},
[screenState]);
在不添加 deps 的情况下编写相同代码的另一种方法是使用 state updater 回调模式
const onScreenChange = useCallback(
(key, value) => {
setScreenState(oldState => {
const newState = Object.assign({}, oldState, { [key]: value });
localStorage.setItem('screens', JSON.stringify(newState));
return newState;
});
},
[]);
但是,如果您绝对确定您尝试做的事情是正确的,您可以选择禁用 deps 警告。
您可以阅读以下帖子以获取更多信息:
推荐阅读
- react-native-android - 在 mac os 中找不到 react-native 命令
- math - 模式识别(肌肉活动)
- ios - 如何在 XCUI 测试自动化框架中组织和分组测试用例
- javascript - 无法使用 process.env 访问反应环境变量
- javascript - 为什么选择只返回第一个值?
- wpf - 将依赖属性绑定到祖先视图模型的属性的正确方法是什么
- mysql - 如何在mysql中踢出具有一半相同约束键的元组
- reactjs - Material-ui FormControlLabel 值不反映更新状态时的变化
- angular - 以角度全局处理 HTTP 错误
- java - 错误:无法找到或加载主类