React 的生命周期就是组件从初始化到卸载的全过程,可以分为以下几个阶段

  1. 初始化阶段
  2. 更新阶段
  3. 卸载阶段


从 React 15 的生命周期,学到 React 17

React 15 的生命周期

React 的 生命周期 - 图1

初始化

四个生命周期钩子

  1. constructor: 常用来初始化 State
  2. componentWillMount:在 render函数生成虚拟 DOM 之前触发
  3. render:通过 Diff 算法,生成新的虚拟 DOM
  4. componentDidMount:组件渲染完成之和触发,这里可以操作真实 DOM

更新阶段

有两种情况会触发更新:

  1. 父组件更新引起组件更新
  2. 自身 state 改变触发的更新

四个生命周期钩子

  • componentWillReceiveProps(nextProps)
    • 父组件更新时,该组件接收到的新 props
  • shouldComponentUpdate(nextProps, nextState)
    • 该方法在组件render前,会被调用,该函数的默认返回的布尔值是true,表示组件要重新render(可用于做性能优化)
  • componentWillUpdate(nextProps, nextState)
    • nextPropsnextState分别表示更新后的,propsstate将是什么值
    • 组件在更新前,会调用的生命周期
  • componentDidUpdate(prevProps, prevState)
    • prevPropsprevState分别表示更新前的,propsstate是什么值
    • 组件在更新后,会调用的生命周期

⭐ 注意:**componentWillReceiveProps(nextProps)**是由父组件的更新触发的,跟 **props**是否变化无关

卸载阶段

一个生命周期钩子

  1. componentWillUnMount:组件卸载前,会执行该函数。可以在这个函数里去清除一些定时器,取消网络请求,清理无效的DOM元素等垃圾清理工作

    这个生命周期钩子,官方不推荐使用,也打算在未来废除

React 16 的生命周期

React 16 废弃了三个生命周期

  • ~~componentWillMount~~
  • ~~componentWillReceiveProps~~
  • ~~componentWillUpdate~~

取而代之的是另外两个生命周期

  • static getDerivedStateFromProps(props, state)
    • 会在调用 render 方法挂载之前调用,会在state更新时会被调用
    • 它应返回一个对象来更新 state,如果返回 null 则不更新任何内容
  • getSnapshotBeforeUpdate(prevProps, prevState)
    • prevPropsprevState分别指 最近一次render前的 propstate
    • 它返回的值将传给 componentDidUpdate的第三个参数

React 的 生命周期 - 图2

初始化

四个生命周期钩子

  • constructor: 常用来初始化 State
  • static getDerivedStateFromProps(props, state)
    • props、 state分别表示组件 render后的 propsstate是什么值
    • 它应返回一个对象来更新 state,如果返回 null 则不更新任何内容
  • render:通过 Diff 算法,生成新的虚拟 DOM
  • componentDidMount:组件渲染完成之和触发,这里可以操作真实 DOM

    更新阶段

    四个生命周期钩子

  • getDerivedStateFromProps(nextProps, nextState)

    • nextProps、 nextState分别表示组件 render后的 propsstate是什么值
    • 它应返回一个对象来更新 state,如果返回 null 则不更新任何内容
  • shouldComponentUpdate(nextProps, nextState)
    • 该方法在组件render前,会被调用,该函数的默认返回的布尔值是true,表示组件要重新render(可用于做性能优化)
  • getShapshotBeforeUpdate(prevProps, prevState)
    • prevPropsprevState分别指 最近一次render前的 propstate
    • 它返回的值将传给 componentDidUpdate的第三个参数
    • 用法并不常见,但它可能出现在 UI 处理中,如需要以特殊方式处理滚动位置的聊天线程
  • componentDidUpdate(prevProps, prevState)
    • prevPropsprevState分别表示更新前的,propsstate是什么值
    • 组件在更新后,会调用的生命周期

      卸载阶段

      一个生命周期钩子
  1. componentWillUnMount:组件卸载前,会执行该函数。可以在这个函数里去清除一些定时器,取消网络请求,清理无效的DOM元素等垃圾清理工作

为什么要改变这几个 API?

  1. 拉钩教育修言老师的回答

说回 getDerivedStateFromProps 这个 API,它相对于早期的 componentWillReceiveProps 来说,正是做了“合理的减法”。做这个减法的决心之强烈,从 getDerivedStateFromProps 直接被定义为 static 方法这件事上就可见一斑。
static 方法内部拿不到组件实例的 this,这就导致你无法在 getDerivedStateFromProps 里面做任何类似于 this.fetch()、不合理的this.setState(会导致死循环的那种)这类可能会产生副作用的操作。
因此,getDerivedStateFromProps 生命周期替代 componentWillReceiveProps 的背后,是 React 16 在强制推行“只用 getDerivedStateFromProps 来完成 props 到 state 的映射”这一最佳实践。
意在确保生命周期函数的行为更加可控可预测,从根源上帮开发者避免不合理的编程方式,避免生命周期的滥用;同时,也是在为新的 Fiber 架构铺路。

参考

《React15和React16生命周期对比,初识Fiber》
《React 官网》