虚拟DOM-Diff算法详解

假如我们想自己实现一个React,简单底层实现:

1.state数据
2.JSX 模板
3.数据 + 模板 结合,生成真实的DOM,来显示
4.state 发生改变
5.数据 + 模板 结合,生成真实的DOM,替换原始的DOM
缺陷:
第一次生成了一个完整的DOM片段
第二次生成了一个完整的DOM片段
第二次的DOM替换第一次的DOM,非常耗性能(实际上可能只有片段中的一小部分需要改变)

那我们应该如何改良呢?

1.state数据
2.JSX 模板
3.数据 + 模板 结合,生成真实的DOM,来显示
4.state 发生改变
5.数据 + 模板 结合,生成真实的DOM,并不直接替换原始的DOM
6.新的DOM和原始的DOM做对比,找差异
7.找出发生了变化的地方
8.只用新的DOM中变化的地方,来替换掉老的DOM中的对应位置
缺陷:
性能的提升并不明显

React提出了第三种方案——虚拟DOM

1.state 数据
2.JSX 模板
3.数据 + 模板结合,生成虚拟DOM(虚拟DOM就是一个JS对象,用它来描述真实DOM)
[ 'div', {id: 'abc'}, [ 'span', {}, 'hello world' ] ]
3.用虚拟DOM的结构生成真实的DOM,来显示

hello world

5.state 发生变化
6.数据 + 模板 生成新的虚拟DOM(极大的提升了性能)
[ 'div', {id: 'abc'}, [ 'span', {}, 'bye bye' ] ]

  1. 比较原始虚拟DOM和新的虚拟DOM的区别,找到区别是span中的内容(极大的提升了性能)
    8.直接操作DOM,改变span中的内容
React的JSX解析过程

JSX -> createElement -> 虚拟DOM(JS对象)->真实的DOM
例如:
return

item

等同于
return React.createElement('div',{},React.createElement('span',{},item));

虚拟DOM带来了什么好处

1.性能提升了
2.它使得跨端应用得以实现(React Native),因为虚拟DOM在原生应用和网页中都能够被识别。

Diff算法

同层比对,如果一层不同,则直接替换,不会做下一层的比对,这样性能比较好

setState是异步的

是为了提升底层的性能。假设我连续调用三次setState,变更三组数据,由于setState是异步的,React可以把三次setState合并成一次,只去做一次虚拟DOM的比对,就可以省去两次虚拟DOM的比对带来的性能的耗费。

key值能用index吗?

react中,我们能不用indexkey值就尽量不用indexkey值,因为这样是不稳定的,我们应该尽量用稳定的不会改变的key值。

你可能感兴趣的:(虚拟DOM-Diff算法详解)