【React】fiber 架构
React Fiber 是 React 16 引入的核心算法重构,旨在解决同步渲染导致的性能瓶颈(如界面卡顿、交互延迟),并支持异步渲染与并发模式。
❗〇、理解任务切片
一秒有60帧,1帧就是16.67毫秒。
浏览器的一帧,也就是16.7ms需要完成的操作:
- 处理各种回调事件(比如click, input…)
- 处理计时器的回调
- 开始帧,准备绘制页面
- 执行requestAnimationFrame动画的回调
- 页面布局、计算合并到主线程
- 绘制完成
- 如果此时还有空闲时i间,执行 requestldleCallback
而 react 恰好就是借鉴了 requestldleCallback 这个函数的思想。相当于它又自己实现了一个类似功能的函数。
⚙️ 一、Fiber 诞生的背景与核心目标
-
同步渲染的瓶颈
旧版 React(Stack Reconciler)采用递归遍历虚拟 DOM 树,过程不可中断。若组件树庞大(如 200 个组件耗时 200ms),主线程会被长期占用,导致用户输入、动画等任务阻塞,引发卡顿。 -
Fiber 的突破方向
- 增量渲染(Incremental Rendering):将耗时渲染任务拆分为可暂停/恢复的小任务单元(Fiber 节点),通过时间分片(Time Slicing)分散到多帧执行,避免阻塞主线程。
- 优先级调度:为任务分配优先级,优先更新用户可以感知的部分(如用户输入 > 动画 > 数据加载),确保高优先级任务即时响应。
🧩 二、Fiber 的核心机制
1. 数据结构:Fiber 节点
每个组件对应一个 Fiber 节点,构成链表树结构(非传统树形),关键属性包括:
child
/sibling
/return
:分别指向子节点、兄弟节点、父节点,形成链表便于中断恢复。stateNode
:关联的真实 DOM 或组件实例。alternate
:指向另一棵 Fiber 树的镜像节点,实现双缓冲。expirationTime
:任务优先级标记,决定调度顺序。effectTag
:副作用标识(如插入、更新、删除)。
2. 双缓冲机制(Double Buffering)
-
Current Tree:当前渲染完成的 Fiber 树,对应实际 UI。
-
WorkInProgress Tree:正在构建的新树,更新完成后与 Current Tree 交换角色,确保更新原子性。
react 通过这两棵树保存更新前后的状态,实现高效对比更新。
3. 两阶段渲染流程
-
Render 阶段(可中断)
- 任务分片:遍历 Fiber 树,逐节点执行
beginWork
(处理组件状态、Diff 子节点)和completeWork
(创建 DOM、收集副作用)。 - 中断恢复:通过全局变量
nextUnitOfWork
记录进度,利用浏览器空闲时间(requestIdleCallback
)分批处理任务。
- 任务分片:遍历 Fiber 树,逐节点执行
-
Commit 阶段(不可中断)
- 同步处理 Render 阶段收集的副作用(如 DOM 更新),一次性提交到界面,避免 UI 不一致。
💎 总结:Fiber 的核心价值
特性 | 解决的问题 | 实现效果 |
---|---|---|
增量渲染 | 主线程阻塞 | 任务分片,避免界面卡顿 |
优先级调度 | 交互响应延迟 | 高优先级任务(如点击)即时处理 |
双缓冲机制 | UI 更新闪烁/不一致 | 原子性切换,确保渲染连贯 |
链表数据结构 | 中断恢复困难 | 通过指针快速定位未完成任务 |