react生命周期

react生命周期

本文整理了有关react生命周期的相关知识,尽量详细而又简单易懂。

一、react生命周期函数?

生命周期函数(钩子函数)就是在某一时刻会被自动的调用执行的函数.
tips:

(1)什么是钩子函数?

百度百科一番:钩子函数是Windows消息处理机制的一部分,通过设置“钩子”,应用程序可以在系统级对所有消息、事件进行过滤,访问在正常情况下无法访问的消息。钩子的本质是一段用以处理系统消息的程序,通过系统调用,把它挂入系统。

总的说,钩子函数是一段程序,是用来处理系统消息的。它的名称是确定的,在系统消息触发时被系统调用,并不是用户自己触发的。如,react的componentDidMount()函数,我们只需要写它的函数体,在组件挂载之后会自动调用此函数。

(2)常见的钩子函数有:react生命周期函数、vue生命周期函数

二、生命周期具体有哪几个阶段?每个阶段都能做什么?

1.constructor(props)

在组件初始化时被调用,可以设置组件的一些初始化的状态以及绑定类方法。

作用:用来初始化状态,如果既不初始化状态也不绑定方法,那就没必要实现该方法了。

tips:
(1)ES6 - class类的继承机制是:先将父类实例的属性、方法加到this上,然后再用子类的构造函数修改this.

(2)子类必须在constructor方法中调用super方法,否则新建一个实例时会报错,因为super在子类中是用来创建父类的this对象,子类的this通过父类构造函数塑造,得到和父类一样的实例属性和方法。简言之,不调用super,子类就得不到this.

(3)若子类中没有constructor,会被默认添加。

2.componentWillMount()

它在render()方法之前被调用,so,也可以用来设置组件内部的状态,因为它不会再次触发组件的渲染。(但是一般还是推荐在constructor中去初始化状态)

3.render()

生命周期中必须有的方法,它把组件的属性和状态作为输入并返回需要渲染的元素,这个元素可以是原生的DOM组件(如div),也可以是一个自定义的组件。

tips:

在此函数中,不能使用setState()方法,否则会造成死循环;

4.componentDidMount()

在组件挂载之后执行一次,这个时候最适合去异步请求API获取数据,将获取到的数据保存在内部组件的状态中使用。

作用:放置必要的DOM节点,可以网络请求、设置定时器、设置状态以致重渲染等

5.componentWillReceiveProps(nextProps)

在一个更新生命周中被调用。新的属性作为它的输入,可以用this.props与之对比之前之后的属性,基于对比结果去实现不同的行为,或是基于新的属性来设置组件的状态。

tips:
(1)componentWillReceiveProps(nextProps)方法的参数nextProps是一个对象,是在更新时父组件传递过来的props;而在这个方法中的nextProps和子组件中每次传递过来的this.props一样都是最新的;

(2)在更新子组件时,componentWillReceiveProps是最先执行的,可以在其内设置setState(),使得render中的值是最新的state值

reactapp中加一个button,值是test,测试componentWillReceiveProps方法

6.shouldComponentUpdate(nextProps, nextState)

每次组件 因为状态或属性更改而 更新时,就会被调用,此时可以执行某些操作,以控制组件是否需要重新render。
tips:
(1)若在父组件state变化,而不想让子组件重新render,可以在此方法中阻止;
(2)如(1)所说,使用shouldComponentUpdate可以避免不必要的render,它是默认返回true(更新)的;当子组件很多且不是每一个子组件都需要重新render时,不可能一个个组件去写阻止的操作,这时可以涉及到React.PureComponent,它是通过props和state的浅对比去实现shouldComponentUpdate(),若对比发现不一致就会update;反之,不会update。
(React.PureComponent是另外的优化性能的知识点了,还得研究研究…)

常用写法:

shouldComponentUpdate(nextProps, nextState) {
	return nextProps.data !== nextState.data;
}

7.componentWillUpdate(nextProps, nextState)

在render()执行之前的最后一个方法,此时已经拥有新的属性和状态,可以进行所需操作,在render渲染之前进行最后的准备呀。
tips:
此方法不要再触发this.setState(),以免造成死循环,如果想要使用新的state更新组件的状态,应该在componentWillReceiveProps中进行相关操作。

8.componentDidUpdate(prevProps, prevState)

在render之后立即调用,可以在这时候进行DOM操作,或是执行更多的异步请求。
tips:
与componentWillUpdate一样,不要在此方法中使用setState()

9.componentWillUnmount()

在组件销毁之前被调用,可以在这时候去执行任何的清理任务。

tips:

(1)销毁组件就是销毁和这个组件有关的状态、事件;

(2)组件内部的状态会随着组件的销毁自动初始化,但是若state保存在redux中,在组件销毁时也要手动销毁state.

三、react生命周期的整体流程是怎样的?执行顺序?

react组件的生命周期总的来说有三个阶段:加载(mount)、更新(update)、卸载(unmount);而每个阶段又有不同的方法,一般地,带有Will字眼的表示该阶段之前发生,带有Did表示在该阶段之后被调用。

1.mount阶段

此阶段表示一个组件实例被创建了,并且插入到DOM中。

在此阶段的方法有:(按顺序调用)

(1)constructor(props):在组件加载之前被调用。

constructor是一个组件类的默认方法,在生成组件实例时会被自动调用

(2)componentWillMount():在组件加载之前被调用。

(3)render():返回一个需要渲染的react元素,这个方法是必须要有的。

(4)componentDidMount():在组件挂载之后被调用。

2.update阶段

此阶段表示一个组件的状态或属性改变了,导致组件重渲染。

此阶段方法有:(按顺序调用)

(1)componentWillReceiveProps():在组件加载完之后,收到新的状态后被调用。

(2)shouldComponentUpdate():组件接收新的属性后调用。

(3)componentWillUpdate():render渲染之前的最后一个方法。

(4)render():同mount阶段的render,只不过在shouldComponentUpdate方法中如果返回false,就不会执行了。

(5)componentDidUpdate():render之后立即调用。

3.unmount阶段

此阶段表示该组件将从DOM中移除。

此阶段的方法有:
componentWillMount():在组件被销毁前调用。

整体流程:
组件第一次渲染之后:
在这里插入图片描述

改变父组件state,子组件也会重新渲染:
在这里插入图片描述
只是改变子组件A:
在这里插入图片描述
销毁子组件A,渲染子组件B:
在这里插入图片描述

四、有什么注意点?

1.不会执行的方法:根组件的componentWillReceiveProps()(因为没有父组件给它传递props,更何况props改变呢);

2.只执行一次的方法:constructor(props)、componentWillmount()、componentDidMount();(也就是mount只会在首次渲染时进行,后面组件状态改变也只会执行update的相关方法)

3.可以执行多次的方法:render()、子组件的componentWillReceiveProps()、componentWillUpdate()、componentDidUpdate();

4.父组件updata,它的子组件也会跟着update(除非在shouldComponentUpdate中return false阻止了,子元素不会重新渲染);子组件update,其父组件不需要update;

5.react会限制嵌套更新的次数,以防止无限循环,so,不要在componentWillUpdate和componentDidUpdate中进行setState操作。

五、容易混淆的周期有哪些?

1.constructor(props)与componentWillMount()

两者都是在组件挂载前被调用,都可以用来设置组件的状态,只不过状态一般在前者中初始化,在后者中可以同步设置状态,也不会触发重渲染。

2.componentDidUpdate 与 componentWillReceiveProps?

componentWillReceiveProps(nextProps) {         
	if(nextProps.count !== this.props.count) {            
	 // doSomething         
	}    
 }
componentDidUpdate(prevProps) {         
	if(prevProps.count !==  this.props.count) {             
		this.setState({ count: this.props.count })       
	 }    
}

主要区别:在react生命周期中的调用时机、更新state的方式(同步还是异步)

componentWillReceiveProps:在组件接收新的props之前触发;在props更改时同步更新组件状态

componentDidUpdate:在组件接收新的props(render)之后触发;更新组件状态是异步的

应用场景:当你希望只有在接收到新props时做一些逻辑时,请使用componentWillReceiveProps,如:根据父组件传入的数据初始化或重置某些内部状态。若希望无论props更改还是组件内容状态更改都能触发一些逻辑,那么请使用componentDidUpdate。

总结:虽然知道有哪些周期,什么时候用,怎么用,但是在真正开发过程中,还是想着要查验一番再着手开发。写此文章一是梳理、总结react生命周期函数相关知识,二是鞭策自己实实在在地掌握好一个知识点。

本文纯属自己查找资料学习和通过项目实践练习完善的,如有哪点不当,请不吝指正呀~

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值