React Hooks 教程之 useEffect
2022-01-12 本文已影响0人
拉基简书已退
目录
React Hooks 教程系列:
正文
功能介绍
useEffect 用于在函数组件中执行副作用
操作,那什么是副作用呢?数据获取,数据订阅,以及手动更改 React 组件中的 DOM 都属于副作用
因为我们渲染出的页面都是静态的,任何在其之后的操作都会对其产生影响,所以称之为副作用,副作用又分为两种:
- 无需清除的副作用
比如发送网络请求,手动变更 DOM,记录日志,这些都是常见的无需清除的操作,因为在执行完这些操作之后就不用管了 - 需要清除的副作用
比如订阅外部数据源,添加 DOM 事件,这种情况下,清除工作是非常重要的,可以防止引起内存泄露
执行时机
useEffect 是在页面渲染完成后执行
useLayoutEffect 是在页面渲染时同步执行
大多数情况下用 useEffect 就够了
函数定义
function useEffect(effect: EffectCallback, deps?: DependencyList): void;
- effect 第一个参数传入一个函数,函数类型为
type EffectCallback = () => (void | Destructor);
- deps 第二个参数传入依赖数组,用于控制第一个参数 effect 的执行时机,下面会详细介绍
使用示例
将 App.tsx 替换为以下代码
import React from "react";
const App: React.FC = () => {
const [state, setState] = React.useState(false);
const [count, setCount] = React.useState(0);
React.useEffect(() => {
console.log("组件创建");
return () => {
console.log("组件销毁");
};
}, [state]);
return (
<>
<div
onClick={() => {
setCount(count + 1);
}}
>
组件 count:{count}
</div>
<div
onClick={() => {
setState(!state);
}}
>
组件 state:{String(state)}
</div>
</>
);
};
export default App;
这里 useEffect 第二个参数传了依赖数组,只有在依赖值变化的时候才会执行第一个参数的函数,可以发现点击“组件 count”不会打印日志,而点击“组件 state”会打印创建和销毁的日志,如下:
然后我们把第二个参数从[state]
改成[]
,刷新页面再点击,可以发现这次无论点击哪个,都不会执行函数了,日志只打印了第一次进入页面的组件创建,如下:
最后我们把第二个参数直接去掉,不传,刷新页面,可以看到这次点击两个都会执行函数,打印创建和销毁的日志,如下:
总结
React.useEffect(() => {
// 创建时执行
return () => {
// 销毁时执行
};
}, [state]); // 依赖列表
依赖列表有三种情况:
- 不传,则每次页面重新渲染都会执行 effect 函数
- 传空数组,则只执行一次 effect 函数,在进入和退出页面时
- 传非空数组,则在数组内依赖值变化时才会执行 effect 函数
总结
相比 Android 和 iOS 动辄六七个生命周期方法,useEffect 只有创建、销毁、更新(依赖数组不传)三个,其实以前 React 类组件也是有多个生命周期方法的,不过从类组件演化到函数组件,简化了不少,这三个已经能覆盖绝大多数开发场景,个人觉得挺好,减少开发者的心智负担