在开始介绍之前,先给大家推荐一个网站https://vue-next-template-explorer.netlify.app。这是Vue3官方演示Vdom的示例网站,本篇文章也是基于它进行演示的。
Vue3 在
Vdom
的更新时,只会关注它有变化的部分。这样的优化使 Vue3 既跳出了 Vdom 的性能瓶颈,又依然保留了可以手写render function
的灵活性。相当于 Vue3 既有 react 的灵活性,又有基于模板的性能保证。——尤雨溪
我们现在来看看同样的html,在vue2和vue3的渲染中对比出不同之处
<div>
<p>空空</p>
<p>{{msg}}</p>
</div>
export function render(_ctx, _cache, $props, $setup, $data, $options) {
return (_openBlock(), _createBlock("div", null, [
// DOM的内容不会变化的元素
_createVNode("p", null, "空空"),
// DOM的内容会变化的元素
_createVNode("p", null, _toDisplayString(_ctx.msg), 1 /* TEXT */)
]))
}
从上述两张图的对比中,我们可以继承
1.vue2中的虚拟DOM是进行全量的对比
2.vue3新增了静态标记(PatchFlags),只对比带有patch flag的节点的虚拟DOM,并且可以通过flag的信息得知当前节点要对比的具体内容
export function render(_ctx, _cache, $props, $setup, $data, $options) {
return (_openBlock(), _createBlock("div", null, [
_createVNode("p", null, "空空"),
_createVNode("p", null, _toDisplayString(_ctx.msg), 1 /* TEXT */)
]))
}
// 把不需要更新的元素,提升出来
const _hoisted_1 = /*#__PURE__*/_createVNode("p", null, "空空", -1 /* HOISTED */)
export function render(_ctx, _cache, $props, $setup, $data, $options) {
return (_openBlock(), _createBlock("div", null, [
_hoisted_1,
_createVNode("p", null, _toDisplayString(_ctx.msg), 1 /* TEXT */)
]))
}