Vue3和Vue2的一些区别
目录
一、main.js文件的不同
二、app.vue组件的不同
三、添加了新的配置项——setup
四、ref函数
五、reactive函数
六、Vue3里面的响应式使用
七、setup函数的注意事项
1.setup函数的执行时间
2.setup函数的参数
八、computed计算属性
九、watch监视函数
1.watch监视ref定义的基本数据类型
2.watch监视reactive定义的对象和数组类型
3.watchEffect智能监视(Vue3里面新添加的)
十、生命周期
十一、toRef函数
十二、其他组合式API
1.shallowReactive
2.shallowRef
3.readonly和shallowreadonly
4.toRaw和markRaw
十三、vue3里面新的组件
1.fragment组件
2.Teleport传送组件
一、main.js文件的不同
我们先分析vue3里main.js文件
注意:vue3的main.js里面不能再写vue2的写法了。
保险起见,还是将Vue3的完整main.js代码贴在这里
二、app.vue组件的不同
我们首先打开一个崭新的vue3 app.vue文件
我们可以清晰的看到<template>标签下没有根div,也就是说:
<vue3组件中的模板标签可以没有根标签>
但是,为了给组件加上样式,我们还是习惯于写上根标签
三、添加了新的配置项——setup
setup是所有组合式api(composition API)表演的舞台
他的值是一个函数
- 组件中的数据(data)、方法(methods)、生命周期等都要配置在setup中
- setup函数的返回值有两种情况:返回一个对象,返回一个渲染函数
- 返回一个对象时,对象里面的东西可以再模板函数里面不加this直接使用(重点关注)
- 返回一个渲染函数时,可以自定义渲染函数的内容(仅作了解)
我们对app.vue文件做如下修改
<template><h1>一个人的信息</h1><h3>姓名:{{ name }}</h3><h3>年龄:{{ age }}</h3><button @click="sayHello">说话</button>
</template><script>export default {name: 'App',setup(){// 再setup里面直接写数据和方法// 数据let name = '张三'let age = 18//方法function sayHello(){alert(`我叫${name}, 我今年${age}岁了,你好啊!`)}return {name,age,sayHello}}}
</script>
这里面就可以看出setup函数的基本用法,注意alert里面的既不是单引号也不是双引号,
注意点:
- vue2的配置不要和vue3混用,会出现问题:
- vue2的配置中可以访问到setup的属性和方法
- 但Vue3的setup配置中不能访问到Vue2的配置(data、methods、computed等)
- 如果Vue2和Vue3的属性名字有重名的,以vue3配置的数据优先
- setup函数不能是一个async函数,因为返回值不再是return的对象,而是promise,模板函数看不到return对象中的属性
四、ref函数
在上一节中,我们这样定义属性:
这不是一个响应式的属性定义方式,如果我们此时用一个函数修改name和age的值,值可以修改,但是页面不会渲染更新之后的内容
使用ref需要先引入
import {ref} from 'vue'
ref封装好的属性会变成一个对象,
这个对象叫做引用实例的实现对象,我们的属性值并不是直接通过对象名字访问的,而是要 对象名.value 访问
但是在模板函数里面 Vue3会帮我们自动.value,所以模板函数里面还是跟原来的差值表达式一样
请看响应式代码
<template><h1>一个人的信息</h1><h3>姓名:{{ name }}</h3><h3>年龄:{{ age }}</h3><button @click="changeInfo">改变内容</button>
</template><script>
import {ref} from 'vue'export default {name: 'App',setup(){// 再setup里面直接写数据和方法// 数据let name = ref('张三')let age = ref(18)function changeInfo(){name.value = '李四'age.value = 48console.log(name,age);}return {name,age,changeInfo}}}
</script>
用ref处理对象的信息,几乎没什么特别的
就不再赘述了
五、reactive函数
在上一节中,我们使用ref函数时们需要不停的使用.value来访问
现在,对于对象数据类型,我们可以使用reactive替换ref, 当然之前还需要引入
在后面访问的时候就不需要加上.value了
我们使用reactive处理数组来简单的示范下
1.先引入
2.给数组添加响应式
3.在setup函数中return给模板函数
4.在函数中修改
优雅,实在是太优雅了
尽管reactive处理数组和对象非常轻松,但是它不能处理基本数据类型(Number, String 等)
解决方法
把所有的数据都封装在一个类里面,面向对象式的存储数据
六、Vue3里面的响应式使用
尚硅谷的老师详细讲解了Vue3的响应式原理以及他和Vue2的不同,方便以后查阅,这里只给出连接
尚硅谷视频=>
在vue3里面,基本数据类型的响应式的使用使用跟vue2没有太大的差别,但是对于数组和对象数据,Vue3的使用方法比vue2要更加简单。
代码
<template><h1>一个人的信息</h1><h3 v-show="person.name">姓名:{{ person.name }}</h3><h3>年龄:{{ person.age }}</h3><h3 v-show="person.sex">性别:{{ person.sex }}</h3><h3>爱好: {{ hobby }}</h3><button @click="addSex">添加性别属性</button><button @click="deleteName">删除name属性</button><button @click="changeInfo">改变内容</button>
</template><script>
import {reactive} from 'vue'export default {name: 'App',setup(){//reactive给对象数据添加响应式let person = reactive({name : '张三',age : 18})//用ref处理对象信息let job = reactive({type:'前端工程师',salay:"30K"})// reactive处理数组属性let hobby = reactive(['抽烟','喝酒','烫头'])// 方法function changeInfo(){hobby[0] = '学习'}function addSex(){person.sex = '男'}function deleteName(){// 从对象里面删除属性delete person.name}return {person,job,hobby,addSex,deleteName,changeInfo}}}
</script>
七、setup函数的注意事项
1.setup函数的执行时间
setup函数的会在beforeCreate生命周期函数之前执行一次,此时this的值时undefined
也就是说,在setup函数里面,我们不能通过this访问到任何东西
2.setup函数的参数
setup函数可以接受两个参数,
- 第一个参数时props对象,用于接收父组件传递过来的数据,单数props对象必须先调用
我们先演示第一个参数:在传递给setup函数之前必须先接收
页面控制台:
这就证明props传递进来的数据是响应式的
接下来演示第二个参数
值得注意的是,在vue3里面,对于具名插槽,我们使用 v-slot:而不是#或者slot="",这只是一个API兼容的问题
我们先从自定义事件开始说起
在App.vue组件里面
在Demo_1.vue组件里面
<template><h1>一个人的信息</h1><h3 v-show="person.name">姓名:{{ person.name }}</h3><h3>年龄:{{ person.age }}</h3><h3 v-show="person.sex">性别:{{ person.sex }}</h3><h3>爱好: {{ hobby }}</h3><button @click="addSex">添加性别属性</button><button @click="deleteName">删除name属性</button><button @click="changeInfo">改变内容</button>
</template><script>
import {reactive} from 'vue'export default {name: 'App',setup(){//reactive给对象数据添加响应式let person = reactive({name : '张三',age : 18})//用ref处理对象信息let job = reactive({type:'前端工程师',salay:"30K"})// reactive处理数组属性let hobby = reactive(['抽烟','喝酒','烫头'])// 方法function changeInfo(){hobby[0] = '学习'}function addSex(){person.sex = '男'}function deleteName(){// 从对象里面删除属性delete person.name}return {person,job,hobby,addSex,deleteName,changeInfo}}}
</script>
注意context组件的写法,context.emit('hello',666);后面是传递的参数
在看vue3组件里面的插槽,这里以具名插槽为例
在Demo.vue组件里面
在App.vue组件里面
具体的使用方法跟vue2没有太大的差别
至于第一项,个人感觉意义不大,毕竟父组件传递参数我们都是要写props来接收的。
八、computed计算属性
跟Vue2的原理基本相同,用法请看代码,不再赘述
<template><h1>一个人的信息</h1>姓:<input type="text" v-model="person.firstName"><br>名:<input type="text" v-model="person.lastName"><br><span>全名:{{ fullName }}</span><br>全名:<input type="text" v-model="person.fullName">
</template><script>
import {computed,reactive} from 'vue'export default {name: 'Demo_1',setup(){let person = reactive({firstName:'张',lastName:'三'})//计算属性//简写版,不考虑计算属性被修改的情况// person.fullName = computed(()=>{// return person.firstName + '-' + person.lastName// })//完整版,计算属性被修改了还可以返回去渲染person.fullName = computed({get(){return person.firstName + '-' + person.lastName},set(value){const NameArr = value.split('-')person.firstName = NameArr[0]person.lastName = NameArr[1];}})return {person,}}}
</script>
get和set实现响应式的原理需要注意
九、watch监视函数
在Vue3中,watch监视函数也是一个组合式API(使用前需先调用),这个函数有三个参数
- 第一个参数是监视的元素
- 第二个参数是监视的回调
- 第三个参数是监视的配置
1.watch监视ref定义的基本数据类型
先简单看一下代码:
<template><div><h3>count的值为:{{ count }}</h3><button @click="count += 1">点我增加count的值</button><button @click="count -= 1">点我减少count的值</button><hr><h3>此时的数据为:{{ msg }}</h3><button @click="msg += '!'">点击修改数据</button></div>
</template><script>
import { ref,watch } from 'vue'export default{setup(){//数据let count = ref(0)let msg = ref('你好啊')//watch监视//因为setup里面没有this,所以我们用回调函数//watch函数第一个参数是监视的元素,第二个参数是监视的回调,第三个参数是监视的配置//情况一,监视ref所定义的响应式数据// watch(count,(NewValue,OldValue)=>{// console.log(`count的值变了,新值为${NewValue},旧值为${OldValue}`);// })//情况二,监视ref定义的多个数据,同时监视多个数据的变化watch([count,msg],(NewValue, OldValue)=>{// console.log(`count或msg的值变了,新值为${NewValue},旧值为${OldValue}`);console.log("count或msg的值变了",NewValue, OldValue);},{immediate:true})return{count,msg}}
}
</script>
跟vue2不同的是,Vue3里面的watgch函数可以不断的被调用,也就是说,在监视多个元素时,我们不仅可以写成数组的形式,还可以直接写还几个watch函数
2.watch监视reactive定义的对象和数组类型
watch监视reactive定义的数据时会出现两个bug,
- watch不能正确的获得OldValue的值,目前这个bug无法解决。
- watch强制开启深度监听,也就是deep配置无效
我们只看第一个bug
我们还是直接看代码、
<template><div><h3>姓名: {{ person.name }}</h3><h3>年龄:{{ person.age }}</h3><button @click="person.name += '~'">修改姓名</button><button @click="person.age++">修改年龄</button></div>
</template><script>
import { reactive,watch } from 'vue'export default{setup(){//数据let person = reactive({name:'张三',age:18})watch(person,(NewValue,OldValue)=>{console.log("person的值变了",NewValue,OldValue);})return{person}}
}
</script>
加入我们要是想单独监视对象里面的某一个属性怎么办呢?
聪明的小伙伴也许已经想到应该怎么办了
但是如果这样写,vue会报出一个警告
并且我们修改age的值时watch也没有监听到
我们应该把这玩意写成一个函数。
这样就成了
3.watchEffect智能监视(Vue3里面新添加的)
watchEffect函数也是一个组合式的api,它不需要指定监视的对象,在他的回调函数里面用了谁他就监视谁,在实际操作中非常方便
简单演示一下
请看下列说明
十、生命周期
在Vue3里面的生命周期钩子既可以写配置项(跟Vue2里面一样),也可以写成组合式API(写在setup 里面)
但是组合式API的优先级更高
具体的跟vue2的差不多,用的也少,所以就不再赘述了.
vue3生命周期API文档=》
图示
十一、toRef函数
vue3里面非常重要的一个API
先看问题:
我们在实现上面几节的代码时,总觉得 person. 写起来很繁琐
所以我们可以在return时对数据做一些处理
我们的意思是在return里面将 person. 写完,在模板函数里面就不用写了。
可是,这样一下,我们发现模板函数里面的响应式功能没了,这是为什么呢?
仔细一想不难发现,我们给name赋值,只是将一串字符串赋值给一个变量而已,跟person里面的属性没有半毛钱关系,也就是说上面的写法就相当于:
我们对name、age、salay变量做修改,根本不会影响到person里面的属性值,这就是页面不渲染响应式的原因
解决办法,那肯定是要使用我们的toRefAPI了
附上完整代码
<template><h3>一个人的信息</h3><h3>姓名:{{ name }}</h3><h3>年龄:{{ age }}</h3><h3>薪资:{{ salay }}K</h3><hr><button @click="name+='~'">修改姓名</button><button @click="age++">增长年龄</button><button @click="salay++">涨薪</button>
</template><script>
import { reactive, toRef } from 'vue'export default{setup(){let person = reactive({name:'张三',age:18,job:{j1:{salay:20}}})return {//使用toRef关键字就可以解决问题name: toRef(person,'name'),age : toRef(person,'age'), salay : toRef(person.job.j1,'salay')}}}
</script>
关于这个API的原理,尚硅谷有很详细的解释
有时候我们需要展出的数据很多,一个一个写又很麻烦了。所以出现了toRefs
值得注意的是,这里的展开只有一层,也就是模板函数里面的salay要这样写
也很方便
十二、其他组合式API
尚硅谷详细介绍=》
1.shallowReactive
顾名思义,这个就是浅层次的reactive
他只确保第一层响应式数据,对于第一次数据里面有对象或数组的,对象或数组里面的属性值就不是响应式的
2.shallowRef
跟上面的shallowReactive一样
当传入的是基本数据类型的时候,shallowRef和ref没有区别,但是当传入的是对象或数组类型的时候,shallowRef不做处理
也就是:shallowRef不处理对象或数组类型
3.readonly和shallowreadonly
readonly是只读的意思,有点类似于const将变量保护起来,不让别人对变量做修改。
可以看看控制台的警告
readonly是深层次的保护,不管是基本数据类型还是对象、数组,只要是再readonly的包裹下都不允许做修改
shallowReadonly是浅层次的保护,对于对象或数组的属性值shallowReadonly不做处理
4.toRaw和markRaw
- toRaw把某个·数据从响应式转化为不是响应式(将响应式的数据还原为其原始的数据)
- markRaw把某个数据标记为非响应式,使其永远也不能成为响应式数据
注意:
- toraw只能处理reactive定义的响应式对象,若是处理ref定义的数据,会变成undefined
十三、vue3里面新的组件
1.fragment组件
原谅孩子太多了敲不下去了~~~
也就是说,vue3自带一个根标签叫做frangment,可以节省空间,提高效率
2.Teleport传送组件
这是我个人很喜欢的一个组件,使用它可以实现弹窗+遮罩层的效果。在很多UI组件库里面也用到了
这个组件的应用我写了另外的一篇博客,请大家移步:
(1条消息) 使用VUE3+teleport组件实现遮罩层和弹窗效果_CTGU_ 21_ emo~~~~的博客-CSDN博客_vue遮罩效果
希望和大家共勉,最后祝大家程序员节快乐~~~~
Vue3和Vue2的一些区别相关推荐
- vue - vue3与vue2.x的区别(一) :目录结构不一致
今天总结一下vue3与vue2.x的区别 -- 目录结构不一致.由于目录结构的不一致相对的也造成了一些问题的存在,比如打包项目之后打开出现白屏现象. 一.目录结构不一致 通过上图可以发现 vu ...
- vue3与vue2的详细区别
1. vue实例化方法改变 vue2通过new Vue(),手动生成.vue3通过createApp实例化 // vue2 import Vue from 'vue':import App from ...
- vue2 怎么用vite_Vue2和Vue3开发组件有什么区别
我们一直都有关注和阅读很多关于Vue3的新特性和功能即将到来.但是我们没有一个具体的概念在开发中会有如何的改变和不一样的体验.还有一些童鞋已经开始又慌又抓狂了 -- "又要开始学新的写法了 ...
- 在 Vue3 成为默认版本后,盘点了 Vue3 与 Vue2 的区别
目录 前言 正文 一.Vue3 与 Vue2 区别概览 二.Vue3 与 Vue2 区别详述 生命周期 多根节点 Composition API 异步组件(Suspense) Teleport 响应式 ...
- Vue3和Vue2的区别
目录 前言 概览 一.新特性 二.差异 详情 一.vue3新特性 1.组合式API---setup 2.ref创建响应式数据 3.Teleport---"传送门" 4.多根节点 5 ...
- Vue3比Vue2有什么优势/区别
优势 性能更好 体积更小 更好的ts支持 更好的代码组织 更好的逻辑抽离 更多新功能 Vue3生命周期 Options API 生命周期 Composition API 生命周期 Options AP ...
- vue3相比vue2效率提升在哪些方面?
vue3相比vue2效率提升在哪些方面? 静态提升 预字符串化 缓存事件处理函数 Block Tree PatchFlag 静态提升 相比vue2,vue3对以下静态节点进行提升: 元素节点 没有绑定 ...
- Windows 切换node版本开发Vue3和Vue2
Windows 切换node版本开发Vue3和Vue2 第一步:先清空本地安装的node.js版本 第二步:安装nvm管理工具(先关掉360等软件,不然会弹出警告!) 1.从官网下载安装包 https ...
- 一个 Java 猿眼中 Vue3 和 Vue2 的差异
随着 TienChin 项目视频的录制,松哥终于也要静下心来,认真捋一捋 Vue3 中的各种新特性了,然后再和小伙伴们进行分享,其实 Vue3 中还是带来了很多新鲜的玩意,今天我们就不卷 Java 了 ...
- vue3和vue2的区别并且如何升级 (对于vue2有基础的)
目录 一.vue3值得注意的新特性 1.1.Teleport 1.2.Vue 3 现在正式支持了多根节点的组件 1.3.自定义事件 emits 1.4.v-model 1.4.1. v-model参数 ...
最新文章
- 解决git 提交出现这个错误fatal: Unable to create ‘project_path/.git/index.lock‘: File exists.
- java条件语句例题_Java-条件语句、循环语句练习
- iOS架构-静态库.a的脚本化打包及使用(3)
- MFC 图片部分透明
- U3D 贴图通道分离后为什么能减小体积
- Windows 环境下 git 客户端中的 git-bash 和 MINGW64
- java 代码scope注解_Spring学习(15)--- 基于Java类的配置Bean 之 @Bean @Scope 注解
- P4980-[模板]Pólya定理
- 如何补充策略与模型在风控中的滞后性
- java 如何去掉http debug日志_你居然还去服务器上捞日志,搭个日志收集系统难道不香么!...
- C#分析URL参数获取参数和值得对应列表(一)
- python爬虫从入门到放弃-python爬虫从入门到放弃(二)- 爬虫的深层原理
- 电脑怎么开护眼模式_心累!整天对着手机电脑,到底该怎么护眼啊啊啊
- html pt兼容,FCKEditor,一个HTML可视化编辑器,兼容很好
- jsp引进的js 显示404_【梅园大讲堂微课堂】Get超级大招!上海人才引进云申报权威解读来了...
- 开关电源之充电器及其线缆的设计控制及测试验证要求
- k3c官改刷openwrt_斐讯K3刷OpenWrt(Lede)
- OutMan——单例模式、代理模式以及iOS沙盒(sandbox)机制
- 使用proteus仿真验证基尔霍夫定律
- 腾讯云直播是什么?操作文档