Virtual DOM这个概念相信大家不会太陌生,他产生的前提是浏览器中的DOM是很“昂贵”的,为了直观的感受,我们可以把一个简单的div
元素属性都打印出来,如下图所示:
<div id="content"></div>
<script>
var div = document.createElement('div')
var str = ''
for(var key in div){
str += key + ' '
}
content.innerHTML = str
</script>
浏览器中DOM
可以看到,真正的DOM元素是非常庞大的,因为浏览器的标准就是把DOM设计的非常复杂。当我们频繁地去做DOM更新,会产生一定的性能问题。
而Virtual DOM就是用一个原生的JS对象去描述一个DOM节点,所以它比创建一个DOM的代价要小的多。在vue.js中,Virtual DOM是用
VNode
这么一个Class
去描述,它是定义在 src/core/vdom/vnode.js
中的。
var VNode = function VNode (
tag,
data,
children,
text,
elm,
context,
componentOptions,
asyncFactory
) {
this.tag = tag;
this.data = data;
this.children = children;
this.text = text;
this.elm = elm;
this.ns = undefined;
this.context = context;
this.fnContext = undefined;
this.fnOptions = undefined;
this.fnScopeId = undefined;
this.key = data && data.key;
this.componentOptions = componentOptions;
this.componentInstance = undefined;
this.parent = undefined;
this.raw = false;
this.isStatic = false;
this.isRootInsert = true;
this.isComment = false;
this.isCloned = false;
this.isOnce = false;
this.asyncFactory = asyncFactory;
this.asyncMeta = undefined;
this.isAsyncPlaceholder = false;
};
可以看到Vue.js中的Virtual DOM还是稍微有点复杂的。因为他这里包含了很多Vue.js的特性。这里千万不要被这茫茫多的属性吓到,实际上Vue.js中Virtual DOM是借鉴了一个开源库snabbdom
的实现,然后加入了一些Vue.js特色的东西。
其实VNode是对真实DOM的一种抽象描述,它的核心定义为非就几个关键属性,标签名,数据,子节点,键值等,其他属性都是用来扩展VNode的灵活性以及实现一些特殊的feature
的。由于VNode只是用来用来映射到真实DOM的渲染,不需要包含操作DOM的方法,因此它就非常轻量和简单。
Virtual DOM除了它的数据结构的定义,映射到真实的DOM实际上要经历VNode的 create、diff 、patch
等过程。
下面是vue.js从初始化到最终渲染的整个过程。假如你想阅读Vue源码,这张图应该能够帮到你。
网友评论