React生命周期

作者: 蓝枫 | 来源:发表于2018-12-20 10:24 被阅读0次

    V16.3之前

    图解

    来自 程墨

    生命周期总览

    react的生命周期大概分为

    • 组件装载(Mount)组件第一次渲染到Dom树
    • 组件更新(update)组件state,props变化引发的重新渲染
    • 组件卸载(Unmount)组件从Dom树删除

    组件装载过程

    • constructor: 在此初始化state,绑定成员函数this环境,props本地化
    • componentWillMount: 预装载函数,不能进行修改state的操作,即使做了,也不会进行新数据状态的渲染。在该函数中做的操作,都可以提前到构造函数中。
    • render: 渲染函数,唯一的一定不能省略的函数,必须有返回值,返回null或false表示不渲染任何DOM元素。它是一个仅仅用于渲染的纯函数,返回值完全取决于this.state和this.props,不能在函数中任何修改props、state、拉取数据等具有副作用的操作。render函数返回的是JSX的对象,该函数并不因为这渲染到DOM树,何时进行真正的渲染是有React库决定的。(setState是一个异步函数)
    • componentDidMount: 挂载成功函数。该函数不会再render函数调用完成之后立即调用,因为render函数仅仅是返回了JSX的对象,并没有立即挂载到DOM树上,而componentDidMount是在组件被渲染到DOM树之后被调用的。另外,componentDidMount函数在进行服务器端渲染时不会被调用。

    组件更新过程

    当组件挂载到DOM树上之后,props/state被修改会导致组件进行更新操作。更新过程会以此调用如下的生命周期函数:

    • componentWillReceiveProps(nextProps): 该函数在组件进行更新以及父组件render函数(不管数据是否发生了改变)被调用后执行,this.props取得当前的props,nextProps传入的是要更新的props。通常是比较this.props和nextProps来重新setState。
    • shouldComponentUpdate(nextProps, nextState): 返回bool值,true表示要更新,false表示不更新,使用得当将大大提高React组件的性能,避免不需要的渲染。
    • componentWillUpdate: 预更新函数。
    • render: 渲染函数。
    • componentDidUpdate: 更新完成函数。
      相比装载过程的生命周期函数,更新过程的生命周期函数使用的相对来说要少一些。常用的是componentWillReceiveProps、componentShouldUpdate,前者经常用于根据前后两个数据去设置组件的状态,而后者则是常用于优化,避免不必要的渲染。

    组件卸载过程

    卸载过程只涉及一个函数componentWillUnmount,当React组件要从DOM树上删除前,会调用一次这个函数。这个函数经常用于去除componentDidMount函数带来的副作用,例如清楚计时器、删除componentDidMount中创造的非React元素。

    注意事项

    setState

    要修改state,只能使用this.setState(),不能使用this.state.value='myData' 类似方式设置state,一是不会驱动重新渲染,二是很可能被后面的操作替换,造成无法预知的错误。此外,React利用状态队列来实现setState的异步更新,避免频繁地重复更新state。当同时做了很多setState操作的时候,react会智能的合并成一个setState,当需要确定的setState完成后的操作,可以使用

        setState({}, () => {
        // 在这里进行state改变后的操作
        })
    

    setState的调用是有风险的,在某些生命周期函数中调用可能会无用甚至早恒循环调用导致崩溃。state的初始化一般在构造函数中实现;setState可以在装载过程的componentWillMount、componentDidMount中调用;setState可以在更新过程中的componentWillReceiveProps、componentDidUpdate中调用

    render

    render是一个异步函数,render执行后并不会直接生成Dom,而是生成虚拟Dom节点(模拟HTML Dom节点的一个javaScript数据结构),何时生成真实的DOM树取决于react框架本身的计算。
    参考 腾讯前端

    V16.3之后

    图解

    图解

    新的生命周期

    getDerivedStateFromProps

    • 触发时间(v16.4修正):组件每次被rerender的时候,包括在组件构建之后(虚拟dom之后,实际dom挂载之前),每次获取新的props或state之后。在v16.3版本时,组件state的更新不会触发该生命周期。
    • 每次接收新的props之后都会返回一个对象作为新的state,返回null则说明不需要更新state.
    • 配合componentDidUpdate,可以覆盖componentWillReceiveProps的所有用法
    • getDerivedStateFromProps是一个静态函数,所以函数体内不能访问this,输出完全由输入决定。
    static getDerivedStateFromProps(nextProps, prevState) {
      //根据nextProps和prevState计算出预期的状态改变,返回结果会被送给setState
    }
    

    getSnapshotBeforeUpdate

    • 触发时间: update发生的时候,在render之后,在组件dom渲染之前。
    • 返回一个值,作为componentDidUpdate的第三个参数。
    • 配合componentDidUpdate, 可以覆盖componentWillUpdate的所有用法。

    删除生命周期

    1. componentWillReceiveProps
    2. componentWillMount
    3. componentWillUpdate

    差异

    所有被删除的生命周期函数,目前还凑合着用,但是只要用了,开发模式下会有红色警告,在下一个大版本(也就是React v17)更新时会彻底废弃。

    生命周期功能替换一览

      static getDerivedStateFromProps(nextProps, prevState) {
        4. Updating state based on props
        7. Fetching external data when props change
      }
      constructor() {
        1. Initializing state
      }
     
      componentDidMount() {
        2. Fetching external data
        3. Adding event listeners (or subscriptions)
      }
      
      shouldComponentUpdate() {
      }
      render() {
      }
      getSnapshotBeforeUpdate(prevProps, prevState) {
        8. Reading DOM properties before an update
      }
      componentDidUpdate(prevProps, prevState, snapshot) {
        5. Invoking external callbacks
        6. Side effects on props change
      }
      
      componentWillUnmount() {
      }
      
      // before
      
      componentWillMount() {
        // 1. Initializing state
        // 2. Fetching external data
        // 3. Adding event listeners (or subscriptions)
      }
      componentWillReceiveProps() {
        // 4. Updating state based on props
        // 6. Side effects on props change
        // 7. Fetching external data when props change
      }
      componentWillUpdate(nextProps, nextState) {
        // 5. Invoking external callbacks
        // 8. Reading DOM properties before an update
      }
    

    参考 程墨

    相关文章

      网友评论

        本文标题:React生命周期

        本文链接:https://www.haomeiwen.com/subject/fsgekqtx.html

        热点阅读