一、性能比2.x快1.2到2倍diff算法的优化vue2中对virtualdom进行了全量对比。在vue3中,增加了静态标签PatchFlag。在创建vnode时,会根据vnode的内容是否可以更改,为其添加一个静态标签PatchFlag。比较时,只会比较具有PatchFlag的节点。PatchFlag有一个类型,比如一个可变的文本节点,它会被添加一个staticflag,它的PatchFlag枚举值为TEXT。这样,diffing时只需要比较文本内容即可。比较的内容比较少。PatchFlag还有动态类、动态样式、动态属性、动态key属性等枚举值。渲染阶段的静态提升(渲染阶段是指生成虚拟dom树的阶段)。在vue2中,一旦检测到数据变化,就会重新渲染组件,重新创建所有vnode,形成新的vdom树。在vue3中,对于不参与更新的vnode,会静态提升,只创建一次,重新渲染时直接复用。静态提升可以理解为在第一次渲染不参与更新的vnode节点时保存它们的引用。当重新渲染一棵新的vdom树时,直接获取它们的引用即可,无需重新创建它们。vue2中缓存了事件监听器,我们写的@click="onClick"也算是一个动态属性,diffing的时候要对比一下。但是我们知道它不会改变,比如变成@click="onClick2",绑定其他值。在vue3中,如果事件没有变化,onClick会被缓存(类似于静态提升达到的效果),节点不会被PatchFlag标记(即不需要更新的节点)。这样在render和diff两个阶段,事件监听属性就省去了不必要的性能消耗。我曾经用一个巨大的dom树来维护一个页面。既然有这么多节点,那么也有很多节点不需要参与更新。在使用vue2的情况下,大量的性能消耗在render和diff这两个阶段。如果当时有vue3,我觉得性能会优化很多。减少创建组件实例的开销。vue2.x每次创建一个实例,数据、props、computed都会暴露在this上,这些都是由Object.defineProperty定义的。这部分操作相当耗时。基于vue3.0中的Proxy,降低了创建组件实例的性能开销。2、按需编译,体积比Vue2.x更小(Treeshaking)在vue3中,可以参考Vue的功能如下。如果你的项目不使用watch,那么treeshaking将在编译期间被移除。import{computed,watch,nextTick}from"vue";使用ES6模块系统导入/导出。3.CompostionAPI:CompositionAPI/InjectionAPI这里需要说一下代码的组织方式。传统网页以html/css/javascript(结构/样式/逻辑)分隔。Vue/React将紧密相关的结构/样式/逻辑以组件化的方式放在一起,有利于代码维护。Compostionapi更进一步,专注于JavaScript(逻辑)部分,将逻辑相关的代码放在一起,方便代码维护。在vue2组件中,代码以OptionAPI风格组织(data/methods/mounted),这样会造成逻辑分散。例如,当我们完成一个计数器功能时,我们必须在data中声明变量并在methodsResponse函数中定义它们,在mounted中初始化变量。如果要在一个功能多、代码量大的组件中维护这样的功能,需要反复切换到data/methods/mounted中对应的位置,然后进行codeChange。在vue3中,使用setup函数。如下图,count相关的逻辑放在counter.js文件中,todo相关的逻辑放在todos.js中。importuseCounterfrom'./counter'importuseTodofrom'./todos'setup(){let{val,todos,addTodo}=useTodo()let{count,add}=useCounter()return{val,todos,addTodo,count,add,在我看来,这是CompostionAPI最大的特点,代码以函数为单位组织的方式。同时它使代码更易于重用。说到重用,CompostionAPI的方式要比mixin的方式好很多。可以清楚的看到组件使用的数据和方法来自于哪个模块,而组件中mixin的功能往往让我们搞不清这个函数来自于哪个mixin。四、更好的TS支持Vue2不适合用ts,因为vue2的OptionAPI风格。options是一个简单的对象,而ts是一个类型系统,面向对象的语法。两者有点不匹配。在结合vue2和ts的具体实践中,我们需要使用vue-class-component加强vue组件,让脚本支持TypeScript装饰器,使用vue-property-decorator添加更多结合Vue特性的装饰器,最后创建ts组件写法和js组件的写法有很大区别。vue3中特制了defineComponent函数,让组件在ts下更好的使用参数类型推断。在CompositionAPI代码风格中,比较有代表性的API是ref和reactive,它们也很好地支持类型声明。import{defineComponent,ref}from'vue'constComponent=defineComponent({props:{success:{type:String},student:{type:ObjectasPropType
