结论
- 生命周期函数里哪些可以
setState
?什么时候setState
合适?- 可以
setState
:componentWillMount
- (虽然这个函数可以,但建议尽量不要在这个函数中执行
setState
,如果可以改成在componentDidMount
执行就尽量放在componentDidMount
中)
- (虽然这个函数可以,但建议尽量不要在这个函数中执行
componentDidMount
componentDidUpdate
componentWillReceiveProps
- 不可以
setState
:componentWillUnmount
shouldComponentUpdate
componentWillUpdate
- 可以
- taro 在正常加载页面前,会先把定义在
src/app.jsx
中的tabBar
页面以及页面包含组件的render
函数都跑一遍- 如上图《Taro-V2.0.5-入口文件生命周期》
- ps:这个执行顺序也是乱的,不确定是哪个页面先,哪个页面后,有时甚至先执行组件的
render
,不确定是不是 bug,暂时没发现有什么问题,如下图:
- 微信小程序生命周期与 taro 生命周期的对应关系
- 适合使用
async
的生命周期函数要满足这两个条件:- 要在
render
函数之后执行 - Taro(React)不关心这个生命周期函数的返回值
- 要在
Why?
对于第一个结论
可以 setState
的生命周期函数:
componentWillMount
componentWillMount
是在render
之前的,如果在这个生命周期函数中执行setState
会有以下两种情况:- 同步执行:
- 对于同步执行的情况,相当于在
render
前修改state
的值,这样写实际上跟直接在constructor
直接修改state
的定义是一样的效果- 如下图:在
constructor
定义的state
值是:“我在 constructor 中定义了 txt 的值”,然后在componentWillMount
上同步修改了state
的值,改成:“我在 componentWillMount 中 同步 修改了 txt 的值”,在render
时就直接用了修改后的值
- 如下图:在
- 对于同步执行的情况,相当于在
- 异步执行:(放在请求的回调函数中)
- 对于异步执行的情况,相当于在页面在“运行中”时,触发了“状态(state)改变”的情况
- 同步执行:
- 页面只挂载一次,在
componentWillMount
里setState
会更新state
一次,而且会和constructor
里的初始化state
合并执行,一定程度上是一次意义不大的setState
,所以虽然在componentWillMount
中可以执行setState
,但个人认为是一种反模式,不建议这样做
componentDidMount
- 页面在“运行中”时,触发了“状态(state)改变”的情况
componentDidUpdate
- 页面在“运行中”时,触发了“状态(state)改变”的情况
componentWillReceiveProps
- 页面在“运行中”时,触发了“状态(state)改变”的情况
不可以 setState
的生命周期函数:
componentWillUnmount
- 页面都要卸载了,在
componentWillUnmount
中执行setState
不会更新state
,不生效并且没有意义
- 页面都要卸载了,在
shouldComponentUpdate
shouldComponentUpdate
里调用setState
会再次触发这个函数,然后在函数中又触发setState
,然后再次触发这个函数,从而死循环
componentWillUpdate
componentWillUpdate
里调用setState
会再次触发这个函数,然后在函数中又触发setState
,然后再次触发这个函数,从而死循环
》》》》》》》》》》》》》》》》》》
对于第四个结论
在 src/app.jsx
中,componentWillMount
、componentDidMount
、componentDidShow
都是在 render
之前,所有如果在这些生命周期函数中加 async
是不会阻断程序去执行 render
的,如下图所示:
同样,如果是在页面上,componentWillMount
是在 render
之前,也会出现以上情况。
另外,如果在 React 关系返回值的生命周期函数中用 async
会有问题:
async shouldComponentUpdate() {
return false; //实际上不会这么写,应该根据state和prop计算出false或者true
}
表面上看,shouldComponentUpdate
返回的是 false
,组件不会被重新渲染,其实,因为函数声明为 async
,所以每次返回的是一个 Promise.resolve(false)
,一个 Promise
对象被转化为 bool
类型,绝对是 true
,所以实际上在React看来 shouldComponentUpdate
返回的永远是 true
。
吴勤发
芦苇科技web前端开发工程师、COO
擅长网站建设、公众号开发、微信小程序开发、小游戏、公众号开发,专注于前端框架、服务端渲染、SEO技术、交互设计、图像绘制、数据分析等研究,有兴趣的小伙伴来撩撩我们~ web@talkmoney.cn
访问 https://www.luweitech.cn/ 了解更多