虚拟DOM是什么

通过JS的Object对象模拟DOM中的节点,然后再通过特定的render方法将其渲染成真实的DOM节点

一个能代表DOM树的对象,通常含有标签名、标签上的属性、事件监听和子元素们,以及其他属性

虚拟DOM优点

  1. 减少DOM操作
    减少次数
    虚拟DOM可以将多次操作合并为一次操作,比如你添加1000个节点,却是一个接一个操作的。
    减少范围
    虚拟DOM借助DOM diff可以把多余的操作省掉,比如你添加1000个节点,目前有990个节点,其实只有10个是新增的
  2. 跨平台
    虚拟DOM不仅可以变成DOM,还可以变成小程序、ios应用、安卓应用,因为虚拟DOM本质上只是一一个JS对象

虚拟DOM缺点

需要额外的创建函数,如createElement或h,但可以通过JSX来简化成XML写法

上面的缺点是,严重依赖打包工具和要添加额外的构建过程

整体来说 :在节点数量小的时候虚拟DOM必DOM快一点。但是如果节点数量达到一个量级时 DOM 就会比虚拟DOM快一点。但是虚拟DOM还可以进行不断的优化。

DOMdiff是什么

比较两棵DOM树的差异是Virtual DOM算法最核心的部分.简单的说就是新旧虚拟dom 的比较,如果有差异就以新的为准,然后再插入的真实的dom中,重新渲染

就是一个patch 函数

  1. patchs =patch(oldVNode,newVNode)

DOMdiff大概逻辑

Tree diff

  • 将新旧两棵树逐层对比,找出哪些节点需要更新
  • 如果节点是组件就看Component diff
  • 如果节点是标签就看Element diff

Component diff

  • 如果节点是组件,就先看组件类型
  • 类型不同直接替换(删除旧的)
  • 类型相同则只更新属性
  • 然后深入组件做Tree diff (递归)

Element diff

  • 如果节点是原生标签,则看标签名
  • 标签名不同直接替换,相同则只更新属性
  • 然后进入标签后代做Tree diff (递归)

比较只会在同层级进行, 不会跨层级比较。

比较后会出现四种情况:

  1. 此节点是否被移除 -> 添加新的节点
  2. 属性是否被改变 -> 旧属性改为新属性
  3. 文本内容被改变-> 旧内容改为新内容
  4. 节点要被整个替换 -> 结构完全不相同 移除整个替换

DOM diff 的优点

同级节点对比

跨平台渲染

DOM diff 的问题

引用方方老师的文章

同级对比会存在BUG

点击这个链接

然后在三个input框里面输入 吴彦祖,刘德华,张学友然后删除2。

25 虚拟 DOM 和 DOM diff - 图1

删除后

25 虚拟 DOM 和 DOM diff - 图2

你会发现删除了3,而不是删除了2 。

这里的计算机里面删除的原理就是:将2替换成3 ,然后删除3

那么怎么解决这个问题呢。

只需要在每个input框设置一个id

代码链接

25 虚拟 DOM 和 DOM diff - 图3

删除后

25 虚拟 DOM 和 DOM diff - 图4