react 生命週期

  • 初始化

一、getDefaultProps()javascript

設置默認的props,也能夠用dufaultProps設置組件的默認屬性.java

二、getInitialState()python

在使用es6的class語法時是沒有這個鉤子函數的,能夠直接在constructor中定義this.state。此時能夠訪問this.propsreact

三、componentWillMount()ios

組件初始化時只調用,之後組件更新不調用,整個生命週期只調用一次,此時能夠修改state。es6

四、 render()ajax

react最重要的步驟,建立虛擬dom,進行diff算法,更新dom樹都在此進行。此時就不能更改state了。算法

五、componentDidMount()axios

組件渲染以後調用,只調用一次。數組

  • 更新

六、componentWillReceiveProps(nextProps)

組件初始化時不調用,組件接受新的props時調用。

七、shouldComponentUpdate(nextProps, nextState)

react性能優化很是重要的一環。組件接受新的state或者props時調用,咱們能夠設置在此對比先後兩個props和state是否相同,若是相同則返回false阻止更新,由於相同的屬性狀態必定會生成相同的dom樹,這樣就不須要創造新的dom樹和舊的dom樹進行diff算法對比,節省大量性能,尤爲是在dom結構複雜的時候

八、componentWillUpdata(nextProps, nextState)

組件初始化時不調用,只有在組件將要更新時才調用,此時能夠修改state

九、render()

組件渲染

十、componentDidUpdate()

組件初始化時不調用,組件更新完成後調用,此時能夠獲取dom節點。

  • 卸載

十一、componentWillUnmount()

組件將要卸載時調用,一些事件監聽和定時器須要在此時清除。

 

 

下面我從constructor構造函數開始,從參數,做用,用法各方面總結

一、constructor

constructor參數接受兩個參數props,context
能夠獲取到父組件傳下來的的props,context,若是你想在constructor構造函數內部(注意是內部哦,在組件其餘地方是能夠直接接收的)使用props或context,則須要傳入,並傳入super對象。

constructor(props,context) { super(props,context) console.log(this.props,this.context) // 在內部可使用props和context } 

固然若是你只須要在構造函數內使用props或者context,那麼只傳入一個參數便可,若是都不能夠,就都不傳。

關於ES6的class constructor和super

只要組件存在constructor,就必要要寫super,不然this指向會錯誤

constructor() { console.log(this) // 報錯,this指向錯誤 } 

二、componentWillMount 組件將要掛載

一、組件剛經歷constructor,初始完數據
二、組件還未進入render,組件還未渲染完成,dom還未渲染

componentWillMount 通常用的比較少,更多的是用在服務端渲染,(我還未使用過react服務端渲染哈,因此也寫不了不少)
可是這裏有一個問題

ajax請求能寫在willmount裏嗎?
:答案是不推薦,別這麼寫

1.雖然有些狀況下並不會出錯,可是若是ajax請求過來的數據是空,那麼會影響頁面的渲染,可能看到的就是空白。
2.不利於服務端渲染,在同構的狀況下,生命週期會到componentwillmount,這樣使用ajax就會出錯

三、componentDidMount 組件渲染完成

組件第一次渲染完成,此時dom節點已經生成,能夠在這裏調用ajax請求,返回數據setState後組件會從新渲染

4.componentWillReceiveProps (nextProps)

componentWillReceiveProps在接受父組件改變後的props須要從新渲染組件時用到的比較多
它接受一個參數

1.nextProps
經過對比nextProps和this.props,將nextProps setState爲當前組件的state,從而從新渲染組件

componentWillReceiveProps (nextProps) {
    nextProps.openNotice !== this.props.openNotice && this.setState({ openNotice:nextProps.openNotice },() => { console.log(this.state.openNotice:nextProps) //將state更新爲nextProps,在setState的第二個參數(回調)能夠打印出新的state }) } 
關於setState的用法及深刻了解 後面會專門整理一篇文章

5.shouldComponentUpdate(nextProps,nextState)

惟一用於控制組件從新渲染的生命週期,因爲在react中,setState之後,state發生變化,組件會進入從新渲染的流程,(暫時這麼理解,其實setState之後有些狀況並不會從新渲染,好比數組引用不變)在這裏return false能夠阻止組件的更新

由於react父組件的從新渲染會致使其全部子組件的從新渲染,這個時候其實咱們是不須要全部子組件都跟着從新渲染的,所以須要在子組件的該生命週期中作判斷

對於react初學者,可能涉及這個生命週期的機會比較少,可是若是你的項目開始注重性能優化,隨着你對react的喜好和深刻,你就會用到這個生命週期

6.componentWillUpdate (nextProps,nextState)

shouldComponentUpdate返回true之後,組件進入從新渲染的流程,進入componentWillUpdate,這裏一樣能夠拿到nextProps和nextState

7.render函數

render函數會插入jsx生成的dom結構,react會生成一份虛擬dom樹,在每一次組件更新時,在此react會經過其diff算法比較更新先後的新舊DOM樹,比較之後,找到最小的有差別的DOM節點,並從新渲染

react16中 render函數容許返回一個數組,單個字符串等,不在只限製爲一個頂級DOM節點,能夠減小不少沒必要要的div(固然注意升級你的react版本,將現有項目升到react16並不會出現什麼bug,惟一注意的是proTypes類型檢測換了名字~)

意思你如今能夠這樣:

render () { return " " 

}
或者這樣:

render () {
  return [ <div></div> <div></div> 

]
}

八、componentDidUpdate(prevProps,prevState)

組件更新完畢後,react只會在第一次初始化成功會進入componentDidmount,以後每次從新渲染後都會進入這個生命週期,這裏能夠拿到prevProps和prevState,即更新前的props和state。
若是你理解了組件一次從新渲染的過程,那麼你應該理解下面5處打印出來的state應該是相同的。(關於setState異步是同步的理解,後面也會整理一篇文章~)

componentWillReceiveProps (nextProps,nextState) {
    this.setState({ fengfeng:nextProps.fengfeng },()=>{ console.log(this.state.fengfeng) //1 }) } shouldComponentUpdate (nextProps,nextState) { console.log(nextState.fengfeng) //2 } componentWillUpdate (nextProps,nextState) { console.log(nextState.fengfeng) //3 } componentDidUpdate (prevProps,prevState) { console.log(this.state.fengfeng) //5 } render () { console.log(this.state.fengfeng) //4 return ( <div></div> ) } 

九、componentWillUnmount ()

componentWillUnmount也是會常常用到的一個生命週期,初學者可能用到的比較少,可是用好這個確實很重要的哦

1.clear你在組建中全部的setTimeout,setInterval
2.移除全部組建中的監聽 removeEventListener
3.也許你會常常遇到這個warning:

Can only update a mounted or mounting component. This usually means you called setState() on an unmounted component. This is a no-op. Please check the code for the undefined component. 

是由於你在組建中的ajax請求返回中setState,而你組件銷燬的時候,請求還未完成,所以會報warning
解決辦法爲

componentDidMount() {
    this.isMount === true axios.post().then((res) => { this.isMount && this.setState({ // 增長條件ismount爲true時 aaa:res }) }) } componentWillUnmount() { this.isMount === false } 

拓展:

1.react生命週期父子組件渲染順序 父子組件, componentWillMount生命週期是先進入父組件仍是子組件? componentDidMount呢?

做者:Evan_zhan 連接:https://www.jianshu.com/p/c9bc994933d5 來源:簡書 簡書著做權歸做者全部,任何形式的轉載都請聯繫做者得到受權並註明出處。
相關文章
相關標籤/搜索