Code前端首页关于Code前端联系我们

Vue Virtual DOM 实现原理

terry 2年前 (2023-09-08) 阅读数 167 #Vue
虚拟DOM /

gkPpCt.pnggkPpCt.png

snabbdom

1。什么是虚拟 DOM 虚拟 DOM

  • 虚拟 DOM 是用常规 JS 对象描述的 DOM 对象
  • DOM 真实成员 - 属性太多
  • 使用虚拟 DOM 来描述真实 DOM
{
    sel: "div",
    data: {},
    children: undefined,
    text: "Hello Virtual DOM",
    elm: undefined,
    key: undefined
}
 

2。为什么要使用虚拟 DOM

  • MVVM框架解决了视图状态同步问题
  • 模板引擎可以简化视图操作,状态无法跟踪
  • DOM虚拟跟踪状态变化

virtual-dom 动机描述 — 请参阅 github 上的 virtual-dom

  • 虚拟DOM可以维护程序状态并跟踪最后的状态
  • 通过比较
  • 前后的两个状态差异来更新实际的DOM

3。虚拟 DOM 的作用

  • 保持视图和状态之间的关系
  • 提高复杂观看情况下的渲染性能
  • 跨平台
    • DOM 浏览器平台渲染
    • 服务器渲染 SSR (Nuxt.js/Next.js)
    • 原生应用程序(Weex/React Native)
    • 小程序(mpvue/uni-app)等

虚拟 DOM 库

  • Snabbdom

    • Vue.js 2.x 中使用的虚拟 DOM 已更改为 Snabbdom
    • 约200个SLOC(一行代码)
    • 可通过模块进行扩展
    • 源码使用TypeScript开发
    • 最快的虚拟 DOM 之一
  • virtual-dom

Diff 算法

快速记忆如下:
四种命中查找
1. 旧前新前
2. 旧后新后
3. 旧前新后
4. 旧后新前

3=> (此项发生了,那么旧前指向的节点,移动到旧后之后)
4=> (此项发生了,那么旧后指向的节点,移动的旧前之前)
 
  • 起始节点和结束节点 - [旧之前新之前,旧之后新之后]

xxxx

  • 旧起始节点/新结束节点 - 【旧正面新背面】

gkSgje.pnggkSgje.png

  • 旧结束节点/新起始节点

gkSbjg.pnggkSbjg.png

  • 不是以上四种情况

gkPpCt.pnggkPpCt.png

  • 循环结束
    • 如果旧节点的所有子节点都先通过(oldStartIdx
    • 先遍历完新节点的所有子节点(newStartIdx > newEndIdx),循环结束

gkFHg0.pnggkFHg0.png

gkk1r8.pnggkk1r8.png

四种类型的节拍搜索

旧与新前
旧与新后
旧与新后
旧与新

3=>(这种情况会发生,然后旧的正面指向的节点移动到旧的背面)

else if (sameVnode(oldStartVnode, newEndVnode)) {
    patchVnode(oldStartVnode, newEndVnode)
    api.insertBefore(parentElm, oldStartVnode.elm, api.nextSibling(oldEndVnode.ele))
}
 

4=>(此项发生,则节点指向old之后,移动到old之前)

版权声明

本文仅代表作者观点,不代表Code前端网立场。
本文系作者Code前端网发表,如需转载,请注明页面地址。

发表评论:

◎欢迎参与讨论,请在这里发表您的看法、交流您的观点。

热门