https://github.com/livoras/blog/issues/13

这里简单记录一些要点和理解:

  一个dom元素中有许多属性,操作dom是很耗资源的,而操作自定义的js对象是很高效。所以在操作dom之间多加一层“虚拟dom”,建立虚拟dom与dom的关联,把直接操作dom转换为操作虚拟dom,然后把最终的虚拟dom关联到dom上,关联的方式是把差异应用到dom上。

  一个js对象来描述一个dom,只需要tagName、props以及children即可。

一个虚拟dom应用,有如下初始化过程

  1. 通过js(如react的jsx)确定好虚拟dom
  2. 根据虚拟dom生成实际的dom树,写到body中  

在js中对虚拟dom进行操作,每次操作会生成一颗新的虚拟dom树,虚拟dom的新树和旧树进行对比,找出差异,然后这些差异会被应用到实际的dom上,完成界面的变更。

对比方式:

  同层次节点对比,深度优先。

差异的类型以及处理方式

  1. 标签名变更,则整个节点统一进行替换,里面的子节点也跟着替换。
  2. 标签的属性变更,把变更的属性应用上去。
  3. 文本节点内容变更,直接替换即可。
  4. 子元素个体的增加、删除、移动。

如何检测子元素个体的变更?

  为每个个体都加上一个标识符key,在当前兄弟节点中这个key要唯一,这样才能在当前的所有children中唯一标识。标识完成后,问题就可以转化为字符串的对比问题了,这里对比只能得出列表的差异(增加删除移动等)。接着继续进行相同key的节点的对比,到这里可见差异的对比是递归的。进行子元素个体的标识,有利于dom的复用,如果不指定,算法会认为两个子元素列表完全不一样,会全部重新渲染,这就很耗费性能了。

“如果元素没有重排,使用数组的索引作为key效果不错”。如何理解这句话呢?

  没重排的意思是,结构体的展示次序不发生变化,而仅仅是结构体中少量属性发生变更。在这种情况下,两个列表元素依次一一对应,找出差异,然后把这些差异按次序应用到列表dom上。如果元素有重排,而且使用了索引作为key,两个列表中相同索引的结构体会完全不同,这样一进行对比,可能会得出一大堆的差异,再将这些差异应用上去可能会比较慢,我感觉其实这些说的都只是相对而已。

如何把差异应用(patch)到实际dom上?

  最开始初始化的时候,根据虚拟dom生成实际的dom,两者的结构层次是一样的,而差异是通过对虚拟dom深度优先对比出来的,应用当然是对实际dom进行深度优先,然后把差异应用上去。

  

虚拟dom和diff算法的更多相关文章

  1. 【React 7/100 】 虚拟DOM和Diff算法

    虚拟DOM和Diff算法 React更新视图的思想是:只要state变化就重新渲染视图 特点:思路非常清晰 问题:组件中只有一个DOM元素需要更新时,也得把整个组件的内容重新渲染吗? 不是这样的 理想 ...

  2. 虚拟DOM与diff算法

    虚拟DOM与diff算法 虚拟DOM 在DOM操作中哪怕我们的数据,发生了一丢丢的变化,也会被强制重建整预DOM树.这么做,涉及到很多元素的重绘和重排,导致性能浪费严重 只要实现按需更新页面上的元素即 ...

  3. vue虚拟dom和diff算法

    vue的虚拟dom和diff算法 1.虚拟dom 虚拟dom,我的理解就是通过js对象的方式来具体化每一个节点,把dom树上面的每个节点都变为对象里的一个元素,元素的子元素变为子节点,节点上面的cla ...

  4. 深入理解react中的虚拟DOM、diff算法

    文章结构: React中的虚拟DOM是什么? 虚拟DOM的简单实现(diff算法) 虚拟DOM的内部工作原理 React中的虚拟DOM与Vue中的虚拟DOM比较 React中的虚拟DOM是什么?   ...

  5. 虚拟dom与diff算法 分析

    好文集合: 深入浅出React(四):虚拟DOM Diff算法解析 全面理解虚拟DOM,实现虚拟DOM

  6. react中虚拟dom的diff算法

    .state 数据 .jsx模板 .生成虚拟dom(虚拟DOM就是一个js对象,用它来描述真实DOM) ['div', {id:'abc'}, ['span', {}, 'hello world']] ...

  7. vue之虚拟DOM、diff算法

    一.真实DOM和其解析流程? 浏览器渲染引擎工作流程都差不多,大致分为5步,创建DOM树——创建StyleRules——创建Render树——布局Layout——绘制Painting 第一步,用HTM ...

  8. 【前端知识体系-JS相关】虚拟DOM和Diff算法

    1.介绍一下vdom? virtual dom, 虚拟DOM 使用JS来模拟DOM结构 DOM变化的对比,放在JS层来做(图灵完备语言),提高效率 DOM操作非常昂贵(消耗性能) 2.Snabbdom ...

  9. 【React自制全家桶】二、分析React的虚拟DOM和Diff算法

    一.React如何更新DOM内容: 1.  获取state 数据 2.  获取JSX模版 3.  通过数据 +模版结合,生成真实的DOM, 来显示,以下行代码为例(简称代码1) <div id= ...

  10. 探究虚拟dom与diff算法

    一.虚拟DOM (1)什么是虚拟DOM? vdom可以看作是一个使用javascript模拟了DOM结构的树形结构,这个树结构包含整个DOM结构的信息,如下图:   可见左边的DOM结构,不论是标签名 ...

随机推荐

  1. Poj2299 Ultra-QuickSort(另附本质不同逆序对)

    Description 给定一个长度为 n(n≤5*10^5) 的序列 a,如果只允许进行比较和交换相邻两个数的操作求至少需要多少次交换才能把 a 从小到大排序. Input The input co ...

  2. java快速排序代码

    public class test1 { public static int partition(int[] array,int lo,int hi){ int key=array[lo]; whil ...

  3. [题解]数学期望_luogu_P1850_换教室

    数学期望dp,题面第一次见很吓人,然而从CCF语翻译成人话就简单多了, 开始一般会想到用 f [ i ] [ j ]表示前 i 个课程申请 j 次的期望,然而其实会发现转移的时候还和上一次的情况有关( ...

  4. C#基础之方法

    方法组成为: public void Fun(string name) { 代码块 } 1.方法的访问级别:修饰符,即上边的Public 2.返回类型:方法是否具有返回值,上边方法无返回值即为void ...

  5. django (四) model模型

    models模型 1. models 定义属性 概述 django根据属性的类型确定以下信息 ·当前选择的数据库支持字段的类型 ·渲染管理表单时使用的默认html控件 ·在管理站点最低限度的验证 dj ...

  6. Django (二) url 和 模板

    1. URL URL地址说明: 使用url给视图函数传参数 在url配置中将正则部分小括号括起来.比如: url(r'^time/plus/(\d{1,2})/$', views.hours_ahea ...

  7. UVa12304(计算几何中圆的基本操作)

    断断续续写了250多行的模拟,其间被其他事情打扰,总共花了一天才AC吧~ 这道题目再次让我明白,有些事情看起来很难,实际上并没有我们想象中的那么难.当然了我主要指的不是这个题的难度…… 也是初学计算几 ...

  8. (洛谷 P1429 平面最近点对(加强版) || 洛谷 P1257 || Quoit Design HDU - 1007 ) && Raid POJ - 3714

    这个讲的好: https://phoenixzhao.github.io/%E6%B1%82%E6%9C%80%E8%BF%91%E5%AF%B9%E7%9A%84%E4%B8%89%E7%A7%8D ...

  9. python学习之图形界面编程:

    一 tkinter:tkinter是python自带的支持tk的库,python代码调用tkinter->tk->操作系统提供的本地GUI(TKL语言开发))完成界面开发,不需要安装任何第 ...

  10. 【algorithm】二叉树的遍历

    二叉树的遍历 二叉树用例 代码解析: public class BinaryTree { static class TreeNode { Integer val; TreeNode left; Tre ...