欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

react16中的hooks的底層實現(xiàn)原理

 更新時間:2025年09月29日 10:06:49   作者:光影少年  
本文主要介紹了react16中的hooks的底層實現(xiàn)原理,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧

好的 ??,你問的是 React 16 中所有 Hooks 的底層實現(xiàn)和原理

這里我會分幾個層次來解釋:

  1. React 16 的背景
  2. Hooks 的設(shè)計理念
  3. 核心 Hooks 的底層實現(xiàn)思路(useStateuseEffectuseContext, …)
  4. React 內(nèi)部的 Hook 數(shù)據(jù)結(jié)構(gòu)
  5. 執(zhí)行流程(函數(shù)組件渲染時 Hook 的調(diào)用順序)

1. 背景:React 16 與 Hooks

  • React 16.8 是第一個支持 Hooks 的版本。
  • 目標(biāo):讓函數(shù)組件具備狀態(tài)(state)和副作用(effect)的能力,替代部分 class 組件邏輯(比如 componentDidMount / componentDidUpdate / componentWillUnmount)。
  • 核心思想通過“調(diào)用順序”來匹配 Hook 與組件的 fiber 節(jié)點,避免顯式 id

2. Hooks 的設(shè)計理念

React Hooks 有幾個原則:

  1. 只能在函數(shù)組件頂層調(diào)用,不能在條件語句或循環(huán)里動態(tài)調(diào)用。
    • 這是因為 Hooks 依賴調(diào)用順序來定位。
  2. 只能在 React 函數(shù)組件或自定義 Hook 中調(diào)用。
  3. 每個組件 fiber 節(jié)點維護一個單鏈表,鏈表節(jié)點就是 Hook 對象。

?? 這就是為什么 eslint-plugin-react-hooks 會強制規(guī)則:不要在 if/for 中調(diào)用 Hook

3. 常見 Hooks 的底層原理

(1)useState

  • 本質(zhì)是 useReducer 的語法糖。
  • 內(nèi)部維護一個 Hook 節(jié)點對象(鏈表的一部分):
type Hook = {
  memoizedState: any,     // 當(dāng)前的 state
  baseState: any,         // 初始 state
  queue: UpdateQueue,     // 更新隊列(鏈表結(jié)構(gòu))
  next: Hook | null       // 指向下一個 Hook
}
  • 當(dāng)你調(diào)用 useState(initial) 時:
    • 創(chuàng)建一個更新對象(action)。
    • 掛到 queue 上。
    • 觸發(fā) scheduleUpdateOnFiber,進入調(diào)度。
    1. React 在當(dāng)前 fiber 上創(chuàng)建一個 Hook 節(jié)點,memoizedState = initial。
    2. 返回 [state, dispatch]。
    3. dispatch 本質(zhì)是一個函數(shù):
  • 渲染時,React 會執(zhí)行 processUpdateQueue,消費 queue,更新 memoizedState

(2)useEffect

  • 保存副作用函數(shù)和依賴數(shù)組。
  • Hook 節(jié)點結(jié)構(gòu):
type Effect = {
  tag: HookFlags,          // effect 類型(Passive, Layout 等)
  create: () => (() => void) | void,  // 副作用函數(shù)
  destroy?: () => void,    // 清理函數(shù)
  deps: any[] | null,      // 依賴
  next: Effect | null
}
  • 調(diào)用 useEffect(fn, deps) 時:
    • 如果 deps 變了,就調(diào)用上一次的 destroy(清理),再執(zhí)行新的 create。
    • 如果沒變,則跳過。
    1. React 在 Hook 節(jié)點里記錄 create 和 deps。
    2. 在 commit 階段(DOM 更新后),React 比較新舊依賴:

(3)useLayoutEffect

  • 和 useEffect 類似,但執(zhí)行時機不同:
    • useLayoutEffect 在 DOM 更新后、瀏覽器繪制前 執(zhí)行(同步)。
    • useEffect 在 瀏覽器繪制后 執(zhí)行(異步,延遲)。
  • 用于測量 DOM、同步操作。

(4)useContext

  • 獲取 Context 的值。
  • 機制:
    • 組件調(diào)用 useContext(MyContext) 時,會在 fiber 上記錄對 MyContext 的依賴。
    • 當(dāng) Context Provider 的值變化時,React 會找到所有依賴它的消費 fiber,觸發(fā)更新。

(5)useReducer

  • 類似 Redux 的 reducer:
    • useState 底層其實就是 useReducer 的特例:

      useState(initial) === useReducer((s, a) => typeof a === 'function' ? a(s) : a, initial)
      
  • 保存 reducer 和 state,通過 dispatch 觸發(fā)更新。

(6)useRef

  • 維護一個 { current: any } 對象,整個生命周期內(nèi)保持引用不變。
  • 實現(xiàn):只在 Hook 節(jié)點里存一個 memoizedState = { current: initialValue },之后不會更新。

(7)useMemo/useCallback

  • 本質(zhì)是“帶緩存的值 / 函數(shù)”。
  • Hook 節(jié)點保存 value 和 deps。
  • 渲染時對比依賴數(shù)組:
    • 如果沒變,直接返回舊值。
    • 如果變了,重新計算并緩存。

4. React 內(nèi)部 Hook 數(shù)據(jù)結(jié)構(gòu)

在 fiber 節(jié)點上,每個函數(shù)組件對應(yīng)一個 Hook 鏈表

type Fiber = {
  memoizedState: Hook | null; // hook 鏈表頭
  updateQueue: any;
  // ...
}
  • renderWithHooks 函數(shù):
    • 進入函數(shù)組件渲染時,初始化 currentlyRenderingFiber
    • 每調(diào)用一個 Hook,就在鏈表上走一步,復(fù)用或新建節(jié)點。
    • 保證 “調(diào)用順序一致 = Hook 順序一致”。

5. Hook 執(zhí)行流程總結(jié)

  1. 初次渲染
    • 執(zhí)行函數(shù)組件,依次調(diào)用 useState / useEffect …
    • 為每個 Hook 創(chuàng)建一個 Hook 節(jié)點,掛到 fiber.memoizedState 鏈表上。
  2. 更新渲染
    • 執(zhí)行組件時,React 會遍歷 fiber.memoizedState 鏈表。
    • 每次調(diào)用 Hook,就拿到對應(yīng)節(jié)點,復(fù)用之前的狀態(tài)。
    • 如果調(diào)用順序錯了(比如把 Hook 放到 if 里),鏈表錯位,React 會報錯。
  3. 提交階段(commit phase)
    • 對于 useEffect / useLayoutEffect,會根據(jù)依賴比較來執(zhí)行副作用。
    • 對于 useState / useReducer,會處理更新隊列,得到新 state。

? 總結(jié):

  • React Hooks 的底層實現(xiàn)是 fiber 節(jié)點上的 Hook 鏈表 + 調(diào)用順序保證。
  • 每個 Hook 維護一個小的狀態(tài)對象,存儲 memoizedState、queuedeps 等。
  • useState 基于更新隊列;useEffect 延遲到 commit 階段執(zhí)行;useRef 只是一個穩(wěn)定對象;useMemo / useCallback 做依賴比較。

到此這篇關(guān)于react16中的hooks的底層實現(xiàn)原理的文章就介紹到這了,更多相關(guān)react16 hooks底層原理內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • React條件渲染實例講解使用

    React條件渲染實例講解使用

    在React中,你可以創(chuàng)建不同的組件來封裝各種你需要的行為。然后還可以根據(jù)應(yīng)用的狀態(tài)變化只渲染其中的一部分。React 中的條件渲染和JavaScript中的一致,使用JavaScript操作符if或條件運算符來創(chuàng)建表示當(dāng)前狀態(tài)的元素,然后讓React根據(jù)它們來更新UI
    2022-11-11
  • React不能將useMemo設(shè)置為默認(rèn)方法原因詳解

    React不能將useMemo設(shè)置為默認(rèn)方法原因詳解

    這篇文章主要為大家介紹了React不能將useMemo設(shè)置為默認(rèn)方法原因詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪<BR>
    2022-07-07
  • react-redux action傳參及多個state處理的實現(xiàn)

    react-redux action傳參及多個state處理的實現(xiàn)

    本文主要介紹了react-redux action傳參及多個state處理的實現(xiàn),文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2022-07-07
  • 詳解React項目中碰到的IE問題

    詳解React項目中碰到的IE問題

    這篇文章主要介紹了React項目中碰到的IE問題,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2019-03-03
  • 實例講解React 組件

    實例講解React 組件

    這篇文章主要介紹了React 組件的相關(guān)資料,文中示例代碼非常詳細(xì),幫助大家更好的理解和學(xué)習(xí),感興趣的朋友可以了解下
    2020-07-07
  • 關(guān)于React項目中的PDF展示解決方案

    關(guān)于React項目中的PDF展示解決方案

    這篇文章主要介紹了關(guān)于React項目中的PDF展示解決方案,具有很好的參考價值,希望對大家有所幫助,如有錯誤或未考慮完全的地方,望不吝賜教
    2024-07-07
  • React Hooks獲取數(shù)據(jù)實現(xiàn)方法介紹

    React Hooks獲取數(shù)據(jù)實現(xiàn)方法介紹

    這篇文章主要介紹了react hooks獲取數(shù)據(jù),文中給大家介紹了useState dispatch函數(shù)如何與其使用的Function Component進行綁定,實例代碼給大家介紹的非常詳細(xì),需要的朋友可以參考下
    2022-10-10
  • React中CSS模塊沖突的問題及解決

    React中CSS模塊沖突的問題及解決

    本文將探討 React 中 CSS 模塊沖突的常見原因,并提供解決方案,具有很好的參考價值,希望對大家有所幫助,如有錯誤或未考慮完全的地方,望不吝賜教
    2025-03-03
  • react類標(biāo)簽的生命周期詳解

    react類標(biāo)簽的生命周期詳解

    在React類組件中,生命周期方法是非常重要的概念,它們允許我們在組件的不同階段執(zhí)行代碼,這包括在組件掛載、更新以及卸載時執(zhí)行的生命周期方法,本文通過介紹React類組件中的生命周期方法,旨在幫助開發(fā)者深入理解組件的生命周期管理
    2024-11-11
  • React Native自定義標(biāo)題欄組件的實現(xiàn)方法

    React Native自定義標(biāo)題欄組件的實現(xiàn)方法

    今天講一下如何實現(xiàn)自定義標(biāo)題欄組件,我們都知道RN有一個優(yōu)點就是可以組件化,在需要使用該組件的地方直接引用并傳遞一些參數(shù)就可以了,這種方式確實提高了開發(fā)效率。對React Native自定義標(biāo)題欄組件的實現(xiàn)方法感興趣的朋友參考下
    2017-01-01

最新評論