javascript - 为什么 React 组件会在状态更改时卸载并重新安装?
问题描述
为什么每次使用 setDrawerOpen 时我的 HomeTypes 组件都会卸载并重新安装?组件内部的状态更改是否总是会导致该组件卸载然后重新安装?
import React, { useEffect, useState } from 'react';
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
import Drawer from '../../components/DrawerComponent/Drawer';
function HomeTypes() {
const [drawerOpen, setDrawerOpen] = useState(null);
useEffect(() => {
console.log('Home Types Mounted');
return () => {
console.log('Home Types Unmounted');
};
});
return (
<div className={`dashboard-page`}>
<h1 className="dashboard-page-title">
Home Types
<button
className={`btn bright primary`}
onClick={() => {
setDrawerOpen(true);
}}>
<FontAwesomeIcon icon={['fas', 'plus']} />
<span>add home type</span>
</button>
</h1>
<Drawer
drawerOpen={drawerOpen}
closeDrawer={() => {
setDrawerOpen(false);
}}
title="Add Home Type"
drawerContent="Hello World"
/>
</div>
);
}
export default HomeTypes;
解决方案
文档请参阅下面的橙色注释:使用效果挂钩
useEffect
每次组件渲染时,钩子都会运行。在挂载时运行一次效果(在卸载时结束清理)[]
以这种形式使用第二个参数运行它:
useEffect(() => {
// Side Effect
return () => {
// Cleanup
}
}, [])
编辑:最好只引用文档
笔记
如果您使用此优化,请确保数组包含组件范围内的所有值(例如 props 和 state),这些值会随时间变化并由效果使用。否则,您的代码将引用以前渲染中的陈旧值。了解更多关于如何处理函数以及当数组变化太频繁时该怎么做。
如果你想运行一个效果并且只清理一次(在挂载和卸载时),你可以传递一个空数组([])作为第二个参数。这告诉 React 你的效果不依赖于任何来自 props 或 state 的值,所以它永远不需要重新运行。这不是作为特殊情况处理的——它直接遵循依赖项数组的工作方式。
如果传递一个空数组 ([]),则效果内的 props 和 state 将始终具有它们的初始值。虽然将 [] 作为第二个参数传递更接近于熟悉的 componentDidMount 和 componentWillUnmount 心理模型,但通常有更好的解决方案来避免过于频繁地重新运行效果。另外,不要忘记 React 会延迟运行 useEffect 直到浏览器绘制完成,所以做额外的工作不是问题。
我们建议在我们的 eslint-plugin-react-hooks 包中使用exhaustive-deps 规则。当依赖项指定不正确时,它会发出警告并建议修复。
推荐阅读
- pytorch - 为什么torch.cuda.device的设备参数可能大于torch.cuda.device_count()?
- lua - 如何使一行代码在循环中运行一次,并且只运行下一行代码,直到前一行运行一次?
- javascript - 将 NProgress 与“React.lazy”一起使用
- c# - “System.IO.File”不包含“ReadLines”的定义
- node.js - 在 Azure AppService 中运行 Angular 应用程序时可能导致“ng:未找到”的原因是什么?
- java - 加载大量文本时加快附加到java swing中的jTextArea
- c# - for (var i = 0; i < count; i++) { } == for (var i = 0; i < count; i++) { }。这是什么符号,为什么要使用它?
- javascript - 我不断收到“不变式失败:浏览器历史记录需要 DOM”错误
- php - $this->_objectProperty 中的下划线是什么意思?
- xml - 解决语法错误,将 XML 内容传输到访问表时缺少运算符