相对于我们开发人员来说,Vue3并不陌生,已经习惯了Vue2开发的前端工程师们注意了,你所知道的Vue3它并不只是Vue一个版本的迭代升级,而是一个质的飞跃,具有划时代里程碑的意义。那我们就简单赘述下吧:

Vue3与Vue2的区别

1.vue2和vue3双向数据绑定原理发生了改变

  • vue2 的双向数据绑定是利用ES5 的一个 API Object.definePropert()对数据进行劫持 结合 发布订阅模式的方式来实现的
  • vue3 中使用了 es6 的 ProxyAPI 对数据代理
    优势如下
    1.defineProperty只能监听某个属性,不能对全对象监听
    2.可以省去for in、闭包等内容来提升效率(直接绑定整个对象即可)
    3.可以监听数组,不用再去单独的对数组做特异性操作 vue3可以检测到数组内部数据的变化
vue3的组件实例代理
vue3对ref的特殊处理

2.vue3支持多节点(这个就不多说了,自行脑补)

3.特有的composition api

这个特性使得Vue3的代码更加统一整齐,也是这个特性让vue文件的编写习惯发生了翻天覆地的变化,看图吧

composition api
option api

4.效率的飞升(开发阶段)

客户端渲染效率比vue2提升了1.3~2倍

SSR渲染效率比vue2提升了2~3倍

面试题:vue3的效率提升主要表现在哪些方面?

静态提升

下面的静态节点会被提升

  • 元素节点
  • 没有绑定动态内容
1
2
3
4
5
6
7
8
9
10
11
// vue2 的静态节点
render(){
createVNode("h1", null, "Hello World")
// ...
}

// vue3 的静态节点
const hoisted = createVNode("h1", null, "Hello World")
function render(){
// 直接使用 hoisted 即可
}

静态属性会被提升

1
2
3
<div class="user">
{{user.name}}
</div>
1
2
3
4
5
6
const hoisted = { class: "user" }

function render(){
createVNode("div", hoisted, user.name)
// ...
}
预字符串化
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
<div class="menu-bar-container">
<div class="logo">
<h1>logo</h1>
</div>
<ul class="nav">
<li><a href="">menu</a></li>
<li><a href="">menu</a></li>
<li><a href="">menu</a></li>
<li><a href="">menu</a></li>
<li><a href="">menu</a></li>
</ul>
<div class="user">
<span>{{ user.name }}</span>
</div>
</div>

当编译器遇到大量连续的静态内容,会直接将其编译为一个普通字符串节点

1
const _hoisted_2 = _createStaticVNode("<div class=\"logo\"><h1>logo</h1></div><ul class=\"nav\"><li><a href=\"\">menu</a></li><li><a href=\"\">menu</a></li><li><a href=\"\">menu</a></li><li><a href=\"\">menu</a></li><li><a href=\"\">menu</a></li></ul>")
image-20200929170205828 image-20200929170304873
缓存事件处理函数
1
<button @click="count++">plus</button>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
// vue2
render(ctx){
return createVNode("button", {
onClick: function($event){
ctx.count++;
}
})
}

// vue3
render(ctx, _cache){
return createVNode("button", {
onClick: cache[0] || (cache[0] = ($event) => (ctx.count++))
})
}
Block Tree

vue2在对比新旧树的时候,并不知道哪些节点是静态的,哪些是动态的,因此只能一层一层比较,这就浪费了大部分时间在比对静态节点上

1
2
3
4
5
6
7
8
9
10
<form>
<div>
<label>账号:</label>
<input v-model="user.loginId" />
</div>
<div>
<label>密码:</label>
<input v-model="user.loginPwd" />
</div>
</form>
image-20200929172002761 image-20200929172555681
PatchFlag

vue2在对比每一个节点时,并不知道这个节点哪些相关信息会发生变化,因此只能将所有信息依次比对

1
2
3
<div class="user" data-id="1" title="user name">
{{user.name}}
</div>
image-20200929172805674
× 我是好人
打赏二维码