React性能優化: 劍走偏鋒(一)

簡介

關於react的性能優化, 可參考的資料不少, 好比:javascript

  • 合理的拆分組件(容器組件, 渲染組件)
  • 合理的數據設計, 只傳遞組件依賴的數據.
  • 使用PureComponent
  • 使用Memo.
  • 使用Immutable數據結構, 提高數據的比較效率
  • 重寫shouldComponentUpdate生命週期.

等等手段, 都有助於提高項目的性能. 這些手段中, 最容易想到, 也最容易實現的, 就是從新shouldComponentUpdate方法.java

場景介紹

一個頁面的容器組件, 依賴幾十個數據對象, 這些數據多是簡單的對象, 也多是複雜對象或immutable對象. 其中store上任何一個數據的更新, 都會引發組件的從新渲染, 而組件的從新渲染, 又可能從新更新store上的數據. 而store上的數據更新, 又會引發其餘組件的從新渲染. 如此循環, 可能致使的問題是, 一個簡單的數據更新, 會引發容器組件以及子組件反覆的渲染. 多達10幾20次的中間臨時渲染. 這些臨時的渲染其實都是沒必要要的.react

解決方案: 優化手段

重寫shouldComponentUpdate生命週期. 永遠都返回false, 最後一次, 手動的調用組件的forceUpdate方法, 更新組件渲染。性能優化

shouldComponentUpdate() {
    clearTimeout(this.timer);
    this.timer = setTimeout(() => {
      this.forceUpdate();
    }, 0);

    return false;
  }
複製代碼

該方法, 看起來看起來很粗暴, 可是效果明顯. 並且簡單. 目前已經運用於項目中. 但該方法有一個不足之處是若是是一個連續的操做, 好比鼠標拖拽, 移動. 操做會有些跳動, 體驗不是很好. 解決的方法是: 針對這類操做, 咱們返回true, 把更新控制權交個react自己. 畢竟這一類的操做佔項目的比例有限, 對咱們的性能影響有限.數據結構

更改後的代碼以下:app

shouldComponentUpdate() {
    // 在作連續操做時, 調用froceUpdate方法會跳動, 致使交互體驗不友好.
    // 針對連續的操做, 咱們在全局設置一個標識, 以開啓默認的react render.
    // 連續的操做: 鼠標拖拽添加frame, 元素旋轉, 元素resize, 移動.
    const globalController = __app['isAutoRender'];
    const isAutoRender = globalController && globalController.isAutoRender;
    if (isAutoRender) {
      return true;
    }

    clearTimeout(this.timer);
    this.timer = setTimeout(() => {
      this.forceUpdate();
    }, 0);

    return false;
  }
複製代碼

若是你也遇到這一類的性能問題, 但願這個方案對你有所幫助.

下一節React性能優化: 劍走偏鋒(二)繼續討論react性能優化問題

相關文章
相關標籤/搜索