react之生命周期函数

流程图

组件创建阶段

static defaultProps

外界没有传入props参数的时候,不会出错。

this.state

在调用构造器的时候就会被调用

componentWillMount

组件的虚拟DOM元素,将要挂载到页面上的时候执行,此时,虚拟DOM还没被创建

render

开始渲染虚拟DOM,当render执行完,虚拟DOM才在内存中创建好
但是此时虚拟DOM并没有挂载到页面上

componentDidMount

表示组件已经挂载,此时的我们的state上的数据 和内存中的虚拟DOM以及
浏览器重的页面,已经保持一致了,组件创建阶段的生命周期函数,执行完毕。
页面第一被渲染好,(一般在这里面可以进行dom节点的操作了)。

执行特点:

只执行一次

组件运行阶段

如果state或者props发生了改变就会出发相应的钩子。

如果属性props改变执行componentWillReceiveProps,
当外界传递给子组件的属性被修改了会触发。

组件接收新属性,此时,只要这个方法触发,就证明父组件为当前子组件传递了新的属性值。

之后触发shouldComponentUpdate(组件是否更新),
如果是则进行如下步骤:
componentWillUpdate(组件将要被更新,还没更新)
->render(重新渲染内存中的DOM对象,此时的DOM树和state已经保持一致了,
但是页面还是旧的)->componentDidUpdate(更新页面)

执行特点:

依据props或state,选择性触发0次或者多次。

组件卸载阶段

componentWillUnmount
组件尚可被使用 还没被卸载。

执行特点:

只执行一次

代码示例

import React from "react";
import ReactTypes from "prop-types"

export default class Counter extends React.Component {
    constructor(props) {
        super(props);
        this.state = {
            msg: "ok",
            count: props.initCount
        }
    }

    //设置组件的默认属性值
    static defaultProps = {initCount: 0}
    //在这个静态对象里可以做类型校验
    //需要第三方包prop-types
    static propTypes = {
        initCount: ReactTypes.number
    }
    handleClick = () => {
        this.setState({
            count: this.state.count + 1
        })
    }

    myselfFunction() {
        console.log("我定义了个函数")
    }

    //组件将要挂载的时候执行,此时虚拟DOM未创建
    componentWillMount() {
        // console.log(this.props.initCount)
        console.log(this.state.msg)
        console.log(this.myselfFunction())
    }

    render() {
        //&&短路运算可以预防undefined引起的异常。
        console.log("ref", this.refs.h3 && this.refs.h3.innerText)

        return <div>
            <h1>这是Counter计数器组件</h1>
            <input type="button" value="+1" id="btn" onClick={() => this.handleClick()}/>
            <hr/>
            <h3 id="myh3" ref="h3">
                当前的数量是:{this.state.count}
            </h3>
        </div>
    }

    componentDidMount() {
        //在这里执行dom的操作
        const h3text = document.getElementById("myh3")
        // h3text.style.background="red"
        // React中不推荐使用元生dom的方式创建click事件
        // const btn = document.getElementById("btn")
        // btn.onclick=()=>{
        //   this.setState({
        //       count:this.state.count+1
        //   })
        // }
        console.log("in componentDidMount", h3text)
    }

    //生命函数创建阶段结束

    //生命周期执行阶段开始
    shouldComponentUpdate(nextProps, nextState, nextContext) {
        //只有return值为true的时候页面才发生变化。
        //为false的时候只改变状态但是页面不更新。
        let flag = false
        console.log("before count", this.state.count)
        //如果奇数true,偶数false
        //页面显示的值比state少1。
        //使用nextState拿最新的值,然后看到网页展示数字只有奇数
        if (nextState.count & 0x1 === 1) {
            flag = true
        } else {
            console.log("...")
        }
        console.log(`in shouldComponentUpdate return value is ${flag}`)

        console.log("after count", nextState.count)
        return flag
    }

    //分支:props改变才会触发
    componentWillReceiveProps(nextProps, nextContext) {
        //举例父组件向子组件传值,第一次的时候不会触发
        console.log("in componentWillReceiveProps")
    }

    //此时虚拟DOM还是旧的内容
    componentWillUpdate() {
        console.log("in componentWillUpdate")
        console.log("ref", this.refs.h3.innerText)

    }

    //接下来执行render重新渲染虚拟DOM

    //此时页面的dom是最新的了
    componentDidUpdate(prevProps, prevState, snapshot) {
        console.log("当前", this.state.count)
    }


}
posted @ 2020-06-26 00:41  公众号python学习开发  阅读(217)  评论(0编辑  收藏  举报