react 之 fiber 架構

尼古拉斯-富贵發表於2024-10-05

一、為什麼要用 fiber架構

 在react16 之前,react是用 diff 演算法對vitrulDom進行對比更新渲染,這種 diff 演算法對比 如果遇到需要大量時間執行的方法任務時,就會造成頁面卡頓

二、什麼是 fiber 架構

 fiber架構簡單點說就是 任務切片(一個耗時任務在瀏覽器空閒時,分多次執行),這樣就在使用者感官上頁面流暢不卡頓

瀏覽器卡頓判斷標準:

正常情況下人眼感受到的 每秒 60幀,也就是16.6ms/幀,如果超過超過這個值,就會感受到卡頓,如果說某個任務耗時超過16.6ms就會造成頁面暫時卡頓

fiber怎麼做:

fiber 架構會把一個要耗時任務會分解成無數個執行只需大概5ms的任務片段,在瀏覽器空閒時執行

如何判斷瀏覽器是否空閒:

瀏覽器有個API叫 requestIdleCallback

requestIdleCallback回撥函式: 回撥函式是在主執行緒空閒時被呼叫的函式。每次呼叫時,都會傳入一個IdleDeadline物件,該物件提供一個timeRemaining()方 法,用來檢測當前幀中剩餘的空閒時間。

注意:requestIdleCallback 是一個宏任務,在事件列表中是最後執行的

but!!!react 並沒有使用瀏覽器原生的 requestIdleCallback 方法(因為瀏覽器相容,目前只要chorm支援)

react 而是用了 MessageChannel 進行任務排程

什麼是 MessageChannel?

MessageChanne設計初衷是為了方便 我們在不同的上下文之間進行通訊,例如web Worker,iframe
它提供了兩個埠(port1 和 port2),透過這些埠,訊息可以在兩個獨立的執行緒之間雙向傳遞

const channel = new MessageChannel();
const port1 = channel.port1;
const port2 = channel.port2;

// 設定 port1 的訊息處理函式
port1.onmessage = (event) => {
    console.log('Received by port1:', event.data);
    port1.postMessage('Reply from port1'); // 向 port2 傳送回覆訊息
};

// 設定 port2 的訊息處理函式
port2.onmessage = (event) => {
    console.log('Received by port2:', event.data);
};

// 透過 port2 傳送訊息給 port1
port2.postMessage('Message from port2');

react 是實現是複雜的,他要設計任務執行優先順序(優先順序設計包含過期時間、是否使用者操作、元件優先順序等)

三、fiber 如何中斷任務

fiber 分片任務執行的兩個階段:

1、排程:任務中斷可以在排程階段進行

2、提交:提交階段任務不能中斷

相關文章