理解React元件的生命週期
本文作者寫作的時間較早,所以裡面會出現很多的舊版ES5的時代的方法。不過,雖然如此並不影響讀者理解元件的生命週期。反而是作者分為幾種不同的觸發機制來解釋生命週期的各個方法,讓讀者更加容易理解涉及到的概念。以下是正文。
簡介
React
在建立元件的時候會觸發元件生命週期各個方法的呼叫。這篇文章就分別介紹其中的各種不同的繪製觸發之後呼叫的各個生命週期的方法。
理解元件的生命週期,你才可以在元件建立、銷燬的時候執行特定的方法。甚至於,你可以決定是否更新元件,正確的處理state
、props
的改變。
生命週期
要弄清楚生命週期,首先就要區分開初次建立和state
、props
更改觸發的元件更新,以及元件的解除安裝。
初始化
初始化 | |
---|---|
√ | initial props |
√ | initial state |
√ | componentWillMount |
√ | render |
√ | componentDidMount |
在ES6裡,initial props在類的constructor
方法裡作為引數傳入了。initial state則在constructor
方法裡有開發者自行設定。如:
class DemoComponent extends React.Component {
constructor(props) {
super(props)
this.state = {
initialState: `value`,
}
this._innerMethod = this._innerMethod.bind(this)
}
}
componentWillMount
方法在render
方法執行之前被呼叫。有一點需要注意,在這裡設定state不會觸發重繪。render
方法返回元件需要的標記(markup),並最終轉化為正確的輸出。props
和state
都不應該在這個方法裡修改。一定要記住render
方法必須是一個純函式。也就是每次呼叫,這個方法都要返回同樣的結果。
當render
方法執行之後就開始執行componentDidMount
方法。DOM
元素(React Native的原生元素)可以在這個方法裡取到。這時可以在這個方法裡執行資料獲取等操作。如果需要的話,任何的DOM操作都可以在這裡執行,絕對不可以在render
方法裡執行。
State改變引發的繪製
State
的修改會觸發一些列的方法:
更新state | |
---|---|
√ | shouldComponentUpdate |
√ | componentWillUpdate |
√ | render |
√ | componentDidUpdate |
shouldComponentUpdate
方法會在render
方法呼叫之前呼叫。在這個方法裡可以控制是否繪製元件,或者直接跳過。顯然,這個方法一定不會在初始化的時候呼叫。在這個方法裡需要返回一個boolean型別的值,預設返回true
。
shouldComponentUpdate(nextProps, nextState) {
return true
}
通過對nextProps
和nextState
的值的處理,可以判定接下來的重繪是否必要。componentWillUpdate
方法在shouldComponentUpdate
方法返回true之後就會被呼叫。在和方法裡任何的this.setState
方法呼叫都是不允許的,因為這個方法是用來為接下來的繪製做準備的,不是用來觸發重繪的。
componentDidUpdate
方法在render
方法之後呼叫。和componentDidMount
方法類似,這個方法裡也可以執行DOM操作。
componentWillUpdate(nextProps, nextState) {
// 為接下來的繪製做準備
}
componentDidUpdate(prevProps, prevState) {
//
}
Props改變引發的繪製
任何對props物件的修改也會觸發生命週期方法的呼叫,這個過程和state的修改引發的生命週期方法基本一致,只是多了一個方法。
更新Props | |
---|---|
√ | componentWillRecieveProps |
√ | shouldComponentUpdate |
√ | componentWillUpdate |
√ | render |
√ | componentDidUpdate |
componentWillRecieveProps
只會在props
物件發生改變並且不是初始繪製的時候呼叫。在這個方法裡,可以根據當前的props
和將要傳入的props
來設定state
,但是這樣並不會觸發繪製。**這個方法裡有個很有趣的地方,在這個方法裡state的相等比較是無效的,因為state的改變不應該引起任何的props的改變。
componentWillReceiveProps(nextProps) {
this.setState({
// 設定state
})
}
其他的生命週期基本上和改變state引起的生命週期方法是一樣的。
解除安裝
解除安裝 | |
---|---|
√ | componentWillUnmount |
我們唯一沒有觸及的方法就是componentWillUnmount
了。這個方法在元件被從DOM中移除之前呼叫。當你需要在元件移除前執行清理操作的時候非常有用。比如,清除timer
之類的物件。