Vue是一套用于构建用户界面的渐进式框架。与其它大型框架(比如Angular),不同之处在于,Vue被设计可以自底层向上逐层应用。Vue的核心库只关注视图层,不仅易于上手,还便于与第三方库或既有的项目整合。另一方面,当与现代化的工具链以及各种支持类库结合使用时,Vue也完全能够为复杂的单页面应用提供驱动。
MVVM架构:
-
View:视图层(UI用户界面);
-
-
Model:数据层(存储数据以及对数据的增删查改);
Vue2对比Vue3
Vue3最有特点的是引进了组合式API(Composition API),此前的2版本,采用的Options API,写业务代码时,实现同一个业务,可能需要写在不同的周期函数中,会导致一个逻辑的代码很分散,可维护性比较差;
Vue3的Composition API可以让用户自由组合,采用hook的方式,把同一个逻辑代码写在一起,增加了可读性;
如图,同一份逻辑代码展示同一背景色,2和3写法的最终效果:
Vue3的新特性介绍
-
重写了双向绑定
-
VDOM性能瓶颈
-
Fragments
-
Tree-Shaking的支持
-
Composition API
一、重写了双向绑定
Vue2 基于 Object.defineProperty()实现,Vue3则基于Proxy;
let proxyObj = new Proxy(obj, {
get: function(target, prop) {
return prop in target ? target[prop] : 0;
},
set: function(target, prop, value) {
target[prop] = value;
},
})
相较之下,有如下优势:
-
丢掉了麻烦的备份数据;
-
省去
for in
循环; -
可以监听数组变化;
-
代码更简洁;
-
可以监听动态新增的属性;
-
可以监听删除的属性;
-
可以监听数组的索引和length属性;
二、Vue3优化Vdom
Vue2中,每次更新进行Diff,都是全量比对,Vue3则只对比有标记的,这样大大减少了非动态内容的对比消耗;
Vue Template Explorer 我们可以通过这个网站看到静态标记
patch flag优化静态树
<span>{{msg}}</span>
<span>Hello world!</span>
<div :id="id">
<span :class="b">Hello world!</span>
</div>
Vue3编译后的Vodm:
export function render(_ctx, _cache, $props, $setup, $data, $options) {
return (_openBlock(), _createElementBlock(_Fragment, null, [
_createElementVNode("span", null, _toDisplayString(_ctx.msg), 1 /* TEXT */),
_createElementVNode("span", null, "Hello world!"),
_createElementVNode("div", { id: _ctx.id }, [
_createElementVNode("span", {
class: _normalizeClass(_ctx.b)
}, "Hello world!", 2 /* CLASS */)
], 8 /* PROPS */, ["id"])
], 64 /* STABLE_FRAGMENT */))
}
新增了patch flag标记:
TEXT = 1 // 动态文本节点
CLASS=1<<1,1 // 2//动态class
STYLE=1<<2,// 4 //动态style
PROPS=1<<3,// 8 //动态属性,但不包含类名和样式
FULLPR0PS=1<<4,// 16 //具有动态key属性,当key改变时,需要进行完整的diff比较。
HYDRATE_ EVENTS = 1 << 5,// 32 //带有监听事件的节点
STABLE FRAGMENT = 1 << 6, // 64 //一个不会改变子节点顺序的fragment
KEYED_ FRAGMENT = 1 << 7, // 128 //带有key属性的fragment 或部分子字节有key
UNKEYED FRAGMENT = 1<< 8, // 256 //子节点没有key 的fragment
NEED PATCH = 1 << 9, // 512 //一个节点只会进行非props比较
DYNAMIC_SLOTS = 1 << 10 // 1024 // 动态slot
HOISTED = -1 // 静态节点
BALL = -2
Vu3在创建Vdom,除了模拟出dom本身的基本信息外,还给它加了一个标记:1 /*TEXT*/
;
这个标记就叫做patch flag(补丁标记);
当Vue的Diff算法走到_createBlock函数时,会忽略所有的静态节点,只对有标记的动态节点进行对比,而且在多层的嵌套下依然有效;
三、Vue3优化Vdom
vue3 允许我们支持多个根节点
<template>
<div>12</div>
<div>23</div>
</template>
同时支持render JSX 写法
render() {
return (
<>
{this.visable ? (
<div>{this.obj.name}</div>
) : (
<div>{this.obj.price}</div>
)}
<input v-model={this.val}></input>
{[1, 2, 3].map((v) => {
return <div>{v}-----</div>;
})}
</>
);
},
同时新增了 Suspense
和 多 v-model
用法;
四、Vue3 Tree shaking
简单来讲,就是在保持代码运行结果不变的前提下,去除无用的代码
在Vue2中,无论我们使用什么功能,它们最终都会出现在生产代码中。主要原因是Vue实例在项目中是单例的,捆绑程序无法检测到该对象的哪些属性在代码中被使用到
而Vue3源码引入tree shaking特性,将全局 API 进行分块。如果你不使用其某些功能,它们将不会包含在你的基础包中
就是比如你要用watch 就是import { watch } from 'vue'
其他的computed 没用到就不会给你打包减少体积
五、Vue 3 Composition Api
Setup 函数式编程 也叫vue Hook
例如 ref reactive watch computed toRefs toRaws,后面学了再转载;
原文链接: