看完后完全了解 Vue 2(2)

文章介绍了Vue3.0中如何使用proxy实现数据双向绑定,以及与Vue2.x相比在性能上的显著改进,包括diff算法优化、静态提升和事件侦听缓存,同时提到了CompostionAPI和更好的TypeScript支持。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

原理:通过ES6的新特性proxy来劫持数据,当数据改变时发出通知

代码:

1

2

3

4

5

6 vue3.0数据双向绑定

7

8

9

10

11

12

13

14

15

16 var obj = {};

17 var obj1 = new Proxy(obj, {

18 // target就是第一个参数obj, receive就是返回的obj(返回的proxy对象)

19 get: function (target, key, receive) {

20 // 返回该属性值

21 return target[key];

22 },

23 set: function (target, key, newVal, receive) {

24 // 执行赋值操作

25 target[key] = newVal;

26 document.getElementById(‘text’).innerHTML = target[key];

27 }

28 })

29 document.addEventListener(‘keyup’, function (e) {

30 obj1[0] = e.target.value;

31 });

32

总结:

Vue2.x版本中的双向绑定不能检测到下标的变化

proxy可以劫持整个对象,并返回一个新对象

2. vue3的亮点

性能比2.x快1.2~2倍
diff算法的优化

在vue2中,虚拟dom是全量比较的。

在vue3中,增加了静态标记PatchFlag。在创建vnode的时候,会根据vnode的内容是否可以变化,为其添加静态标记PatchFlag。diff的时候,只会比较有PatchFlag的节点。PatchFlag是有类型的,比如一个可变化文本节点,会将其添加PatchFlag枚举值为TEXT的静态标记。这样在diff的时候,只需比对文本内容。需要比对的内容更少了。PatchFlag还有动态class、动态style、动态属性、动态key属性等枚举值。

render阶段的静态提升(render阶段指生成虚拟dom树的阶段)

在vue2中,一旦检查到数据变化,就会re-render组件,所有的vnode都会重新创建一遍,形成新的vdom树。

在vue3中,对于不参与更新的vnode,会做静态提升,只会被创建一次,在re-render时直接复用。

静态提升可以理解为第一次render不参与更新的vnode节点的时候,保存它们的引用。re-render新vdom树时,直接拿它们的引用过来即可,无需重新创建。

事件侦听缓存

在vue2中,我们写的@click="onClick"也是被当作动态属性,diff的时候也要对比。但我们知道它不会变化,比如变成@click=“onClick2”,绑定别的值。

在vue3中,如果事件是不会变化的,会将onClick缓存起来(跟静态提升达到的效果类似),该节点也不会被标记上PatchFlag(也就是无需更新的节点)。这样在render和diff两个阶段,事件侦听属性都节约了不必要的性能消耗。

我曾经维护过一个拥有很庞大dom树的页面。由于节点非常多,无需参与更新的节点也很多,使用vue2的情况下,在render和diff两个阶段,消费了很多性能,如果当时有vue3的话,我想性能会被优化很多。

减少创建组件实例的开销

vue2.x每创建一个实例,在this上要暴露data、props、computed这些,都是靠Object.defineProperty去定义的。这部分操作还是挺费时的。

vue3.0中基于Proxy,减少了创建组件实例的性能开销。

按需编译,体积比Vue2.x更小(Tree shaking)

在vue3中,可以如下面这样引用vue的功能函数,如果你的项目没有用到watch,那编译时就会把tree shaking掉。

import { computed, watch, nextTick } from “vue”;

利用的就是 ES6 模块系统import/export。

Compostion API: 组合API/注入API

这里要说到代码的组织方式,传统的网页是html/css/javascript(结构/样式/逻辑)分离。vue/react通过组件化的方式,将联系紧密的结构/样式/逻辑放在一起,有利于代码的维护。

compostion api更进一步,着力于JavaScript(逻辑)部分,将逻辑相关的代码放在一起,近而有利于代码的维护。

在vue2的组件内,使用的是Option API风格(data/methods/mounted)来组织的代码,这样会让逻辑分散,举个例子就是我们完成一个计数器功能,要在data里声明变量,在methods定义响应函数,在mounted里初始化变量,如果在一个功能比较多、代码量比较大的组件里,你要维护这样一个功能,就需要在data/methods/mounted反复的切换到对应位置,然后进行代码的更改。

在vue3中,使用setup函数。如下所示跟count相关的逻辑,都放到counter.js文件里,跟todo相关的逻辑放到todos.js里。

import useCounter from ‘./counter’

import useTodo from ‘./todos’

setup(){

let { val, todos, addTodo } = useTodo()

let {count,add} = useCounter()

return {

val, todos, addTodo,

count,add,

}

}

在我看来这就是Compostion API最大的特点,以功能为单位的代码组织方式。同时它可以让代码更易重用。

说到重用,Compostion API的方式也比mixin的方式好很多,你可以清楚的看到组件使用的数据和方法来自哪个模块,而mixin进组件的功能,常常会让我们困惑此功能来自哪个mixin。

更好的TS支持

vue2不适合使用ts,原因在于vue2的Option API风格。options是个简单对象,而ts是一种类型系统、面向对象的语法。两者有点不匹配。

在vue2结合ts的具体实践中,要用 vue-class-component 强化 vue 组件,让 Script 支持 TypeScript 装饰器,用 vue-property-decorator 来增加更多结合 Vue 特性的装饰器,最终搞的ts的组件写法和js的组件写法差别挺大。

在vue3中,量身打造了defineComponent函数,使组件在ts下,更好的利用参数类型推断 。Composition API 代码风格中,比较有代表性的api就是 ref 和 reactive,也很好的支持了类型声明。

import { defineComponent, ref } from ‘vue’

const Component = defineComponent({

props: {

success: { type: String },

student: {

type: Object as PropType,

required: true

}

},

setup() {

const year = ref(2020)

const month = ref<string | number>(‘9’)

month.value = 9 // OK

const result = year.value.split(‘’) // => Property ‘split’ does not exist on type ‘number’

}

自定义渲染API(Custom Renderer API)

vue2.x架构问题

vue2.x最开始支持运行在浏览器中,渲染到浏览器的dom上,随着vue的流行,出现了weex和myvue。

  • weex:移动端跨平台方案,需要渲染到移动设备。weex被写在vue原项目里,缺点是这使vue原项目更大了,也不是通用解决方案。

  • myvue:小程序上使用,需要渲染到小程序框架上。myvue是单独fork一份源代码进行更改,缺点也非常明显,myvue中vue的版本跟官方版本从fork的那一刻开始,就要开始不一致了。

vue2.x项目架构对于这种渲染到不同平台不太友好,vue3.0推出了自定义渲染API解决了该问题。

下面我们先看vue2和vue3的入口写法有所不同:

// vue2

文末

技术是没有终点的,也是学不完的,最重要的是活着、不秃。

零基础入门的时候看书还是看视频,我觉得成年人,何必做选择题呢,两个都要。喜欢看书就看书,喜欢看视频就看视频。

最重要的是在自学的过程中,一定不要眼高手低,要实战,把学到的技术投入到项目当中,解决问题,之后进一步锤炼自己的技术。

自学最怕的就是缺乏自驱力,一定要自律,杜绝“三天打鱼两天晒网”,到最后白忙活一场。

高度自律的同时,要保持耐心,不抛弃不放弃,切勿自怨自艾,每天给自己一点点鼓励,学习的劲头就会很足,不容易犯困。

技术学到手后,找工作的时候一定要好好准备一份简历,不要无头苍蝇一样去海投简历,容易“竹篮打水一场空”。好好的准备一下简历,毕竟是找工作的敲门砖。

拿到面试邀请后,在面试的过程中一定要大大方方,尽力把自己学到的知识舒适地表达出来,不要因为是自学就不够自信,给面试官一个好的印象,面试成功的几率就会大很多,加油吧,骚年!

开源分享:【大厂前端面试题解析+核心总结学习笔记+真实项目实战+最新讲解视频】

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值