参数介绍
- 第一个参数为副作用函数
- 第二个参数为依赖项
import { useState, useEffect } from 'react'
export default function TestEffect() {
useEffect(()=>{
console.log('useEffect1')
})
useEffect(()=>{
console.log('useEffect2')
return ()=>{
console.log('useEffect2卸载')
}
})
useEffect(()=>{
console.log('useEffect3')
return ()=>{
console.log('useEffect3卸载')
}
},[])
return (
<div>TestEffect</div>
)
}
输出:
非StrictMode下
useEffect1
useEffect2
useEffect3
StrictMode下
useEffect1
useEffect2
useEffect3
useEffect2卸载
useEffect3卸载
useEffect1
useEffect2
useEffect3
这里只研究下非StrictMode模式,首先执行useEffect将副作用函数加入队列等待执行,挂载后依次执行副作用函数
清理函数
副作用函数的返回值是可选的,一般用来返回一个清理函数,用来清理副作用
清理函数执行时机
清理函数会在组件卸载时以及下一次副作用函数调用之前执行
import { useState, useEffect } from 'react'
export default function TestEffect() {
let [num,setNum] = useState(0)
useEffect(()=>{
console.log('useEffect1')
})
useEffect(()=>{
console.log('useEffect2')
return ()=>{
console.log('useEffect2卸载')
}
})
useEffect(()=>{
console.log('useEffect3')
return ()=>{
console.log('useEffect3卸载')
}
},[])
return (
<div>
<p>{num}</p>
<button onClick={()=>setNum(++num)}>change</button>
</div>
)
}
点击change按钮,依次打印useEffect2卸载
,useEffect1
,useEffect2
import { useState } from "react";
import TestEffect from './TestEffect'
export default function App() {
let [show,setShow] = useState(true)
return <div>
{show && <TestEffect/>}
<button onClick={()=>setShow(false)}>destroy</button>
</div>;
}
点击destory按钮,依次打印useEffect2卸载
,useEffect3卸载
总结
function FunctionLifecycle(props){
const [ num , setNum ] = useState(0)
React.useEffect(()=>{
/* 请求数据 , 事件监听 , 操纵dom , 增加定时器 , 延时器 */
console.log('组件挂载完成:componentDidMount')
return function componentWillUnmount(){
/* 解除事件监听器 ,清除 */
console.log('组件销毁:componentWillUnmount')
}
},[])/* 切记 dep = [] */
React.useEffect(()=>{
console.log('props变化:componentWillReceiveProps')
},[ props ])
React.useEffect(()=>{ /* */
console.log(' 组件更新完成:componentDidUpdate ')
})
return <div>
<div> props : { props.number } </div>
<div> states : { num } </div>
<button onClick={ ()=> setNum(state=>state + 1) } >改变state</button>
</div>
}
export default ()=>{
const [ number , setNumber ] = React.useState(0)
const [ isRender , setRender ] = React.useState(true)
return <div>
{ isRender && <FunctionLifecycle number={number} /> }
<button onClick={ ()=> setNumber(state => state + 1 ) } > 改变props </button> <br/>
<button onClick={()=> setRender(false) } >卸载组件</button>
</div>
}
- useEffect有两个参数,分别为副作用函数,依赖项
- 只指定副作用函数,相当于
componentDidMount
和componentDidUpdate
- 指定副作用函数同时指定依赖项为空数组,相当于
componentDidMount
- 清理函数会在卸载以及下一次副作用函数调用前执行
- 指定依赖项为props,相当于componentDidUpdate