Vue Diff 算法原理
1. 面试题
Q: Vue 的 Diff 算法是怎样的?Vue 2 和 Vue 3 有什么区别?
2. 核心解答
Vue 的 Diff 发生在 Virtual DOM Patch 阶段,采用同层对比策略。
(1) Vue 2:双端对比 (Double-ended)
Vue 2 使用 4 个指针:旧头、旧尾、新头、新尾。
通过 4 种组合(头头、尾尾、头尾、尾头)进行对比尝试。
- 场景:如果不幸都没命中,再通过 key 去旧列表中查找。
- 优势:非常适合处理反转列表、首尾追加等常见操作,效率很高。
(2) Vue 3:快速 Diff (Quick Diff)
Vue 3 引入了更先进的 最长递增子序列 (LIS) 算法。
- 预处理:先把头部和尾部的相同节点处理掉(Sync Sequence)。
- 核心计算:对于中间乱序的部分,生成一个 source 数组,计算最长递增子序列。
- 序列中的节点位置不动。
- 其他节点移动到序列的间隙中。
- 优势:相比 Vue 2,Vue 3 能计算出最少的 DOM 移动次数。
(3) Key 的重要性
如果不加 Key,Vue 默认采用就地复用策略(只更新文本,不移动节点)。
- 后果:会导致组件状态(如输入框内容)残留错位,过渡动画失效。
- 必须加 Key:让 Diff 算法能识别节点的身份,从而正确地复用、移动或删除。
3. 总结
- Vue 2: 双端指针算法。
- Vue 3: 最长递增子序列 (LIS) 算法,移动次数更少。
- 原则: 列表渲染必加唯一 Key。