1. 程式人生 > >React Native入門(十三)之元件的生命週期

React Native入門(十三)之元件的生命週期

前言

React Native中元件的生命週期,也就是React.js中Component的生命週期。
英文官方文件:React.Component
類比Android中activity和fragment,瞭解其生命週期對於我們掌握一個元件從建立到銷燬的整個完整的過程和優化邏輯有很大的幫助。

圖解

首先來一張經典的生命週期的圖:
這裡寫圖片描述
(圖片來自這裡
在圖中可以看出大概分為3個階段:

首先getDefaultProps建立前的準備工作,來設定預設props的值,所以嚴格地來說,這不是元件的生命週期的一部分。需要注意的是如果有從父元件傳過來的同名的props,那麼會覆蓋。還有就是多個例項間共享引用

,而不是有多個!
另外,在ES6中使用defaultProps替代了getDefaultProps,如:

static defaultProps = {
        name: 'mars',
        sex: 'boy',
        age: 10
};//設定預設屬性

import PropTypes from 'prop-types';

static propTypes = {
        name: PropTypes.string.isRequired,
        sex: PropTypes.string,
        age: PropTypes.number,
};//設定屬性的型別

①建立例項化階段
這個階段才是元件生命週期真正開始的階段。主要有元件例項建立,初始化狀態,掛載渲染等過程。
在ES6中,初始化state放在了constructor建構函式中,而不再使用getInitialState,如:

constructor(props){
  super(props);
  this.state = {
    like:false
  };
}

②執行更新階段
這個階段主要是用來處理使用者互動事件,元件接收父元件props更新或者state改變,介面更新。這個階段是生命週期中最重要的階段,我們常在這一階段對元件進行優化,減少render,從而大大提高效能!
③銷燬階段
這一階段比較簡單,只有一個回撥函式,在元件銷燬

的時候呼叫!這裡主要做一些元件的解除安裝銷燬操作,最典型的比如定時器!

各個階段回撥函式

defaultProps就不再說了,基本上也就上邊說的那點內容,而且不算是生命週期的一部分!

建立例項化階段

constructor() (ES6)

建構函式,元件建立時呼叫,寫法就是上邊那種格式,super(props)一定要寫在第一行。然後使用:

this.state={
  xx:xx,
  xx:xx,
};

來初始化狀態!

componentWillMount()

該回調方法在元件掛載前呼叫!這個函式呼叫時機是在元件建立,並初始化了狀態之後,在第一次繪製 render() 之前。可以在這裡做一些業務初始化操作,也可以設定元件狀態。這個函式在整個生命週期中只被呼叫一次。

render()

元件渲染的時候呼叫!只允許返回一個最外層容器元件。render函式儘量保持純淨,只渲染元件,不修改狀態,不執行副操作(比如計時器)。所以我們不要在render()函式裡邊做一些更改狀態或者與伺服器互動的操作!

componentDidMount()

元件掛載之後呼叫!需要注意的是,RN 框架是先呼叫子元件的 componentDidMount(),然後呼叫父元件的函式。這個函式裡我們就可以與伺服器進行互動,進行網路請求載入資料的操作,或者與 JS 其他框架互動了,例如設定計時setTimeout

執行更新階段

componentWillReceiveProps(object nextProps)

該回調函式在接收到新的props時呼叫,一般是由父元件傳遞過來的!引數nextProps是接收的到新的props,當前舊的屬性還是可以通過 this.props 來獲取。在這個回撥函式裡面,你可以根據屬性的變化,通過呼叫 this.setState() 來更新你的元件狀態,這裡呼叫更新狀態是安全的,並不會觸發額外的 render() 呼叫

shouldComponentUpdate(object nextProps, object nextState)

該函式返回一個布林值!由上圖中可以看出,在接收到父元件屬性,或者每次state更改的時候,都會呼叫該函式!
如果返回ture,則進行元件的重新渲染render,相反返回false,則不做任何處理!
預設情況下,這個函式永遠返回 true 用來保證資料變化的時候 UI 能夠同步更新。但是在某些特定條件下,我們可以過載這一方法根據傳遞過來的props和state來選擇是否更新,從而提高效能。

說到這裡,順便提一下PureComponent,我們知道最常見的一般extends Component來寫一個元件,如果我們知道這一元件不需要重繪或者其他改變的props或者state跟這個元件沒有關係的話,我們可以使用extends PureComponent來避免重繪!
因為PureComponent內部已經幫我們實現了shouldComponentUpdate()函式!
原始碼:

// 這個變數用來控制組件是否需要更新
var shouldUpdate = true;

// inst 是元件例項
if (inst.shouldComponentUpdate) {
  shouldUpdate = inst.shouldComponentUpdate(nextProps, nextState, nextContext);
} else {
  if (this._compositeType === CompositeType.PureClass) {
    // 用 shallowEqual 對比 props 和 state 的改動
    // 如果都沒改變就不用更新
    shouldUpdate =
      !shallowEqual(prevProps, nextProps) ||
      !shallowEqual(inst.state, nextState);
  }
}

需要注意的是shallowEqual()是淺比較,那麼涉及到一些物件,陣列的話,還是需要我們自己寫邏輯判斷的!

componentWillUpdate(object nextProps, object nextState)

shouldComponentUpdate返回true或者呼叫forceUpdate之後,就會開始準更新元件,並呼叫 componentWillUpdate()
輸入引數與shouldComponentUpdate一樣,在這個回撥中,可以做一些在更新介面之前要做的事情。需要特別注意的是,在這個函式裡面,你就不能使用 this.setState 來修改狀態。這個函式呼叫之後,就會把 nextPropsnextState 分別設定到 this.propsthis.state 中。緊接著這個函式,就會呼叫 render() 來更新介面了。

render()

跟初始化的時候一樣,渲染函式。

componentDidUpdate(object prevProps,object prevState)

元件更新渲染完成之後,就會呼叫改回調函式!因為到這裡已經完成了屬性和狀態的更新了,此函式的輸入引數變成了 prevProps 和 prevState。
同樣的,這裡也不能使用 this.setState 來修改狀態

銷燬階段

componentWillUnmount()

元件被解除安裝的時候呼叫。一般在componentDidMount裡面註冊的事件需要在這裡刪除。比如定時器,監聽等!

更新方式

此部分內容來自:React元件生命週期小結,寫的很好,這裡學習記錄一下!
在react中,觸發render的有4條路徑

以下假設shouldComponentUpdate都是按照預設返回true的方式。

  • 首次渲染Initial Render
  • 呼叫this.setState (並不是一次setState會觸發一次render,React可能會合並操作,再一次性進行render)
  • 父元件發生更新(一般就是props發生改變,但是就算props沒有改變或者父子元件之間沒有資料交換也會觸發render)
  • 呼叫this.forceUpdate()

這裡寫圖片描述
注意,如果在shouldComponentUpdate裡面返回false可以提前退出更新路徑。

總結

對生命週期進行一個整體的回顧:
這裡寫圖片描述

上邊的內容是在查閱一些資料文件部落格之後的一個學習總結,對自己瞭解元件生命週期有很大的幫助,也非常感謝這些前輩的指引!

相關推薦

React Native入門十三元件生命週期

前言 React Native中元件的生命週期,也就是React.js中Component的生命週期。 英文官方文件:React.Component 類比Android中activity和fragment,瞭解其生命週期對於我們掌握一個元件從建立到銷燬的整

React Native入門列表元件的使用(2)關於FlatList的一切

前言 在上一篇部落格中瞭解了列表元件的相關內容,主要是靜態的展示了一個列表資料,瞭解了ScrollVIew,FlatList和SectionList的基本用法,本篇文章就深入的瞭解一個常用的一個列表元件FlatList的用法! 屬性 新增頭部元件

React Native入門安裝,環境搭建

介紹 安裝 ①安裝Chocolatey Chocolatey是一個Windows上的包管理器,類似於linux上的yum和 apt-get。 官網:https://chocolatey.org/ 安裝步驟,點選這裡,官網上提供兩種方式,

React Native入門網路請求Fetch

前言 最近有些事情要忙,RN相關的內容沒有更新,現在就來了解一下RN中進行網路請求相關的內容! 介紹 React Native提供了和web標準一致的Fetch API,用於滿足開發者訪問網路的需求。 關於Fetch API的相關內容,可以到下邊網站

React Native入門使用Flexbox佈局

前言 flex,收縮,彈性的意思。 彈性(Flex)寬高 關於RN中寬高的設定,我們在上一篇設定Image載入網路圖片的時候提到過,首先width和height是兩個屬性,用來指定一個元件的寬高,使用的時候可以這樣: <Image source

React Native 入門

當前 RN 版本:0.49 操作環境:Windows 10 Props(屬性)是元件在被建立的時候就能夠使用的各種引數,通常是該元件被使用時傳遞過來的或者是該元件已經設定的預設引數。 傳遞屬性 我們有兩個檔案 App.js 和 MyVie

React Native入門十二使用第三方字型檔案

前言 專案中需要展示一些別的平面或者其他民族文字時,需要使用該文字對應的字型檔案,一般來說都是.ttf的。 在React Native中,使用字型檔案就是在style中設定fontFamily屬性! 比如,這裡的字型檔案為:FangSong.ttf,那麼使

React Native入門十一螢幕適配

準備 首先,我們在官方文件寬度和高度一節可以知道,RN中單位是dp,這個跟Android中的單位是一致的! 官網中: A dp is equal to one physical pixel on a screen with a density of 1

Python爬蟲從入門到放棄十三 Scrapy框架的命令行詳解

directory xpath idf 成了 spider i386 名稱 4.2 不同的 這篇文章主要是對的scrapy命令行使用的一個介紹 創建爬蟲項目 scrapy startproject 項目名例子如下: localhost:spider zhaofan$ sc

04 React快速入門——元件拆分

問題描述:       在目前存在的例項中,程式碼結構如下圖所示:        在index.js中引入了TodoList.js中定義的元件來實現頁面上的一個簡單佈局,一個輸入框和一個按鈕,通過點選按鈕來依次將

React-Native 基礎使用style定義元件的樣式

style是一個props style的鍵值命名格式遵循CSS風格,除了名字使用駝峰法則而不是使用分隔符。例如背景色:backgoundColor,不是background-color 可以傳遞style陣列,最後一個style有優先權,因而可以使用它繼承

React Native探索使用fetch進行網絡請求

數據處理 boolean from convert light util javascrip content import 前言 React Native可以使用多種方式來進行網絡請求,比如fetch、XMLHttpRequest以及基於它們封裝的框架,fetch可以說是替

Spring入門IoC

使用 bsp martin 需要 容器 nbsp 依賴註入 tin 這就是 一、IoC定義   IoC,即控制反轉。開發者在使用類的實例之前,需要先創建對象的實例。但是IoC將創建實例的任務交給IoC容器,這樣開發應用代碼時只需要直接使用類的實例,這就是IoC。在討論控制反

Shell入門數組

定義 col 元素 array 多維 開始 code logs shel 一、一維數組   bash支持一維數組(不支持多維數組),並且沒有限定數組的大小。   類似與C語言,數組元素的下標由0開始編號。 二、定義數組 在Shell中,用括號來表示數組,數組元素用"空格

linux十三磁盤分區、創建文件系統、掛載

動作 打開 oot mage 允許 關閉自動 def ubun mount 前面學習了linux的用戶管理 ,感覺是不是linux的多用戶多任務的系統感覺十分了解了,但是其實並不然的。你還需要了解更多。接下來給大家分享的是 在vmware中添加硬盤創建分區,然後掛載到指定

MySQL十三MySQL事務

發出 最簡 -i 更改 讀取數據 兩種方法 mysql ont 之間 前言   這段時間自己會把之前學的東西都總結一遍,希望對自己以後的工作中有幫助。其實現在每天的狀態都是很累的,但是我要堅持!   進入我們今天的正題:   為什麽MySQL要 有事務呢?事務到底是用

React Native學習—— 對接七魚客服

clas render round 外部文件 bubuko source his 代碼 veh 本文基於React Native 0.52 Demo上傳到Git了,有需要可以看看,寫了新內容會上傳的。Git地址 https://github.com/gingerJY/Rea

react-native 學習

androi bsp ger net devel 瀏覽器 sim 百度 解決方法 上一節講到了 react-native的開發環境的配置,,這一節我門具體講講怎麽看樣式,怎麽調試 看樣式的話 有一個 神奇 react-native-developer tools(個人推薦,

react-native 學習

-s 樣式 dimens screen gpo 像素 github php 我們 上一次講到了react-native 的配置環境 和 如何去進行調試,這一次我們說一說,關於react-native的 樣式兼容問題。 由於iphonex的發售,在兼容的時候,我門也需要去考慮

React Native學習—— 使用Flexbox布局

styles BE art 分享圖片 category urn def ger p s 本文基於React Native 0.52 Demo上傳到Git了,有需要可以看看,寫了新內容會上傳的。Git地址 https://github.com/gingerJY/React-N