面试官:说说 Real DOM和 Virtual DOM 的区别?优缺点?
huihuiha opened this issue · 13 comments
一、是什么
Real DOM,真实DOM
, 意思为文档对象模型,是一个结构化文本的抽象,在页面渲染出的每一个结点都是一个真实DOM
结构,如下:
Virtual Dom
,本质上是以 JavaScript
对象形式存在的对 DOM
的描述
创建虚拟DOM
目的就是为了更好将虚拟的节点渲染到页面视图中,虚拟DOM
对象的节点与真实DOM
的属性一一照应
在React
中,JSX
是其一大特性,可以让你在JS
中通过使用XML
的方式去直接声明界面的DOM
结构
const vDom = <h1>Hello World</h1> // 创建h1标签,右边千万不能加引号
const root = document.getElementById('root') // 找到<div id="root"></div>节点
ReactDOM.render(vDom, root) // 把创建的h1标签渲染到root节点上
上述中,ReactDOM.render()
用于将你创建好的虚拟DOM
节点插入到某个真实节点上,并渲染到页面上
JSX
实际是一种语法糖,在使用过程中会被babel
进行编译转化成JS
代码,上述VDOM
转化为如下:
const vDom = React.createElement(
'h1',
{ className: 'hClass', id: 'hId' },
'hello world'
)
可以看到,JSX
就是为了简化直接调用React.createElement()
方法:
-
第一个参数是标签名,例如h1、span、table...
-
第二个参数是个对象,里面存着标签的一些属性,例如id、class等
第三个参数是节点中的文本
通过console.log(VDOM)
,则能够得到虚拟VDOM
消息
所以可以得到,JSX
通过babel
的方式转化成React.createElement
执行,返回值是一个对象,也就是虚拟DOM
二、区别
两者的区别如下:
- 虚拟DOM不会进行排版与重绘操作,而真实DOM会频繁重排与重绘
- 虚拟DOM的总损耗是“虚拟DOM增删改+真实DOM差异增删改+排版与重绘”,真实DOM的总损耗是“真实DOM完全增删改+排版与重绘”
拿以前文章举过的例子:
传统的原生api
或jQuery
去操作DOM
时,浏览器会从构建DOM
树开始从头到尾执行一遍流程
当你在一次操作时,需要更新10个DOM
节点,浏览器没这么智能,收到第一个更新DOM
请求后,并不知道后续还有9次更新操作,因此会马上执行流程,最终执行10次流程
而通过VNode
,同样更新10个DOM
节点,虚拟DOM
不会立即操作DOM
,而是将这10次更新的diff
内容保存到本地的一个js
对象中,最终将这个js
对象一次性attach
到DOM
树上,避免大量的无谓计算
三、优缺点
真实DOM
的优势:
- 易用
缺点:
- 效率低,解析速度慢,内存占用量过高
- 性能差:频繁操作真实DOM,易于导致重绘与回流
使用虚拟DOM
的优势如下:
-
简单方便:如果使用手动操作真实
DOM
来完成页面,繁琐又容易出错,在大规模应用下维护起来也很困难 -
性能方面:使用Virtual DOM,能够有效避免真实DOM数频繁更新,减少多次引起重绘与回流,提高性能
-
跨平台:React借助虚拟DOM, 带来了跨平台的能力,一套代码多端运行
缺点:
- 在一些性能要求极高的应用中虚拟 DOM 无法进行针对性的极致优化
- 首次渲染大量DOM时,由于多了一层虚拟DOM的计算,速度比正常稍慢
参考文献
你好,请问一下,’最终将这个js对象一次性attach到DOM树上‘ , 这句话 不是很理解。
具体是怎么操作的?
Update the DOM tree all change in once
请问一下这句话怎么理解:React借助虚拟DOM, 带来了跨平台的能力,一套代码多端运行
请问一下这句话怎么理解:React借助虚拟DOM, 带来了跨平台的能力,一套代码多端运行
就是把dom转为js对象的形式来体现dom树,这个js对象是可以转化为不同端的具体真实Dom的。
请问一下这句话怎么理解:React借助虚拟DOM, 带来了跨平台的能力,一套代码多端运行
简单的理解就是 虚拟dom实际上是一个结构固定的js对象,借助自定义的babel转换成对应的东西,比如在type="div" 加载到html里可以转成div 在小程序你可以转成view。
真实dom 效率低,解析速度慢,内存占用量过高。 这个怎么理解???
请问一下这句话怎么理解:React借助虚拟DOM, 带来了跨平台的能力,一套代码多端运行
同问
请问一下这句话怎么理解:React借助虚拟DOM, 带来了跨平台的能力,一套代码多端运行
同问
react的虚拟dom用到了移动端,网页端,服务端。
真实dom 效率低,解析速度慢,内存占用量过高。 这个怎么理解???
如果单论操作一次真实dom的过程,原生的肯定比react执行的快,毕竟原生的没有执行虚拟dom这一层操作,但是如果操作多次的话,原生的需要频繁的查询dom,这是比较费时间的,采用虚拟dom的话,更新的过程是很快的,然后一次性的添加到页面里面。
这里的 优缺点描述有误导性。
Real DOM 和 Virtual DOM 的对比,需要在其应用场景中来对比的。
如果仅仅是 对DOM的一次修改,或者 低频次的,低复杂度的 修改,那么 Real DOM 的 性能肯定是要高于 Virtual DOM 的。
而如果是 复杂场景,需要频繁的,高频次的修改, 那么 Virtual DOM 就可以提供 一种相对于 DOM tree 更简单的 对象树结构 来描述 Real DOM,为 复杂场景 的 DOM 更新提供 基础支持,可以在基于 Virtual DOM 的基础上采用 Diff 算法,收集在某一段时间内的需要更新的DOM,将 复杂场景下可能存在的 频繁修改整个DOM Tree 带来的性能开销 优化为 集中更新需要修改的DOM,从而从整体上带来 性能提升。
而效率是否高效,这个要结合怎么去用 Virtual DOM 的,比如 React, 比如 Vue,是 它们 对比 Real DOM 使我们的效率得到了提升。
虚拟DOM不会进行排版与重绘操作,而真实DOM会频繁重排与重绘
这段话的频繁触发重排与重绘,最好说成频繁触发重排或重绘。因为不是所有操作都会触发重排。
请问一下这句话怎么理解:React借助虚拟DOM, 带来了跨平台的能力,一套代码多端运行
虚拟dom就是js对象,可以被解释成android和ios或其他端的组件或代码
同志们不要误导人了,虚拟dom不会比直接操作dom快, 它的最有用的部分是跨平台能力,虚拟dom 处理后最后还是操作dom,所以不可能比直接操作dom快,平时说的比真实dom快,可以理解为可以减少不必要的dom操作,从而可提升性能。通过虚拟dom的diff算法减少不必要的dom操作,用js性能换dom操作的性能, 因为dom操作是一个性能很不好的操作,可以理解为 dom操作很慢