因为它是异步 Promise 调用,所以你必须使用可变引用变量(使用 useRef)检查已卸载的组件以进行下一步的异步响应处理(避免内存泄漏):
警告:无法对已卸载的组件执行 React 状态更新。
在这种情况下您应该使用两个 React Hooks:useRef
and useEffect
.
With useRef
,例如,可变变量_isMounted
总是指向内存中的同一个引用(不是局部变量)
useRef如果需要可变变量,则为首选钩子。与本地不同
变量,React 确保在每个变量期间返回相同的引用
使成为。如果你愿意的话,也是一样的类组件中的 this.myVar
例子 :
const login = (props) => {
const _isMounted = useRef(true); // Initial value _isMounted = true
useEffect(() => {
return () => { // ComponentWillUnmount in Class Component
_isMounted.current = false;
}
}, []);
function handleSubmit(e) {
e.preventDefault();
setLoading(true);
ajaxCall = Inertia.post(window.route('login.attempt'), values)
.then(() => {
if (_isMounted.current) { // Check always mounted component
// continue treatment of AJAX response... ;
}
)
}
}
同时,让我向您解释有关此处使用的 React Hooks 的更多信息。另外,我还将比较功能组件(React >16.8)中的 React Hooks 与类组件中的 LifeCycle。
使用效果:大多数副作用发生在钩子内部。副作用的示例包括:数据获取、设置订阅以及手动更改 DOM React 组件。 useEffect 替换了 Component 类中的很多 LifeCycle(componentDidMount、componentDidUpate、componentWillUnmount)
useEffect(fnc, [dependency1, dependency2, ...]); // dependencies array argument is optional
-
useEffect 的默认行为在第一次渲染后运行(如 ComponentDidMount)并在每次更新渲染后(如 ComponentDidUpdate)如果你没有依赖关系。就像那样 :useEffect(fnc);
-
为 useEffect 提供一系列依赖项将改变其生命周期。在此示例中:useEffect 将在第一次渲染后以及每次计数更改时调用一次
导出默认函数 () {
const [count, setCount] = useState(0);
useEffect(fnc, [count]);
}
-
useEffect 将在第一次渲染后仅运行一次(如 ComponentDidMount)如果您放置一个空数组作为依赖项。就像那样 :useEffect(fnc, []);
-
为了防止资源泄漏,当钩子的生命周期结束时,所有的东西都必须被处理掉(如 ComponentWillUnmount)。例如,如果依赖项为空数组,则返回的函数将在组件卸载后调用。就像那样 :
使用效果(()=> {
返回fnc_cleanUp; // fnc_cleanUp 将取消所有订阅和异步任务(例如:clearInterval)
}, []);
useRef:返回可变的引用对象 whose .current财产是
初始化为传递的参数 (initialValue)。返回的对象
将在组件的整个生命周期中持续存在。
示例:对于上面的问题,我们不能在这里使用局部变量,因为它会丢失并在每次更新渲染时重新启动。
const login = (props) => {
let _isMounted= true; // it isn't good because of a local variable, so the variable will be lost and re-defined on every update render
useEffect(() => {
return () => {
_isMounted = false; // not good
}
}, []);
// ...
}
所以,结合useRef and 使用效果,我们可以彻底清理内存泄漏。
您可以阅读有关 React Hooks 的更多内容的好链接是:
[EN] https://medium.com/@sdolidze/the-iceberg-of-react-hooks-af0b588f43fb https://medium.com/@sdolidze/the-iceberg-of-react-hooks-af0b588f43fb
[FR] https://blog.soat.fr/2019/11/react-hooks-par-lexemple/ https://blog.soat.fr/2019/11/react-hooks-par-lexemple/