复杂data的处理方式
◼ 我们知道,在模板中可以直接通过插值语法显示一些data中的数据。
◼ 但是在某些情况,我们可能需要对数据进行一些转化后再显示,或者需要将多个数据结合起来进行显示;
比如我们需要对多个data数据进行运算、三元运算符来决定结果、数据进行某种转化后显示;
在模板中使用表达式,可以非常方便的实现,但是设计它们的初衷是用于简单的运算;
在模板中放入太多的逻辑会让模板过重和难以维护;
并且如果多个地方都使用到,那么会有大量重复的代码;
例如:
div id="app">
<!-- 拼接名字 -->
<!-- 方式一:使用插值语法表达式直接拼接-->
<h2>姓名:{{firstName +" "+lastName}}</h2>
<h2>{{firstName}}{{lastName}}</h2>
<!-- 2.显示分数等级 -->
<h2>{{score >=60?"及格":"不及格"}}</h2>
<!--3.反转单词显示文本 -->
<h2>{{message.split(" ").reverse().join()}}</h2>
</div>
<!-- 引入本地vue文件 -->
<script src="./lib/vue.js"></script>
<script>
// 创建app
const app = Vue.createApp({
data(){
return{
// message:"Hello Vue"
//1.姓名
firstName:"Kobe",
lastName:"bryant",
// 2.分数:根据分数显示及格/不及格
score:80,
// 2.一串文本:对文本中的单词进行反转显示
message:"my name is hdc"
}
},
})
// 挂载app
app.mount("#app")
```
◼ 我们有没有什么方法可以将逻辑抽离出去呢?
可以,其中一种方式就是将逻辑抽取到一个method中,放到methods的options中;
例如:
<div id="app">
<!-- 拼接名字 -->
<!-- 方式一:使用methods函数调用拼接-->
<h2>姓名:{{getFullName()}}</h2>
<h2>{{getFullName()}}</h2>
<!-- 2.显示分数等级 -->
<h2>{{scoreLevel()}}</h2>
<!--3.反转单词显示文本 -->
<h2>{{formartArr()}}</h2>
</div>
<!-- 引入本地vue文件 -->
<script src="./lib/vue.js"></script>
<script>
// 创建app
const app = Vue.createApp({
data(){
return{
// message:"Hello Vue"
//1.姓名
firstName:"Kobe",
lastName:"bryant",
// 2.分数:根据分数显示及格/不及格
score:80,
// 2.一串文本:对文本中的单词进行反转显示
message:"my name is hdc"
}
},
methods:{
getFullName(){
return this.firstName +" "+this.lastName
},
scoreLevel(){
if(this.score >=60){return "及格"}
return "不及格"
},
formartArr(){
return this.message.split(" ").reverse().join(" ")
}
}
})
// 挂载app
app.mount("#app")
但是,这种做法有一个直观的弊端,就是所有的data使用过程都会变成了一个方法的调用;
另外一种方式就是使用计算属性computed;
认识计算属性computed
<div id="app">
<!-- 拼接名字 -->
<!-- 方式一:使用methods函数调用拼接-->
<h2>姓名:{{fullName}}</h2>
<h2>{{fullName}}</h2>
<!-- 2.显示分数等级 -->
<h2>{{scoreLevel}}</h2>
<!--3.反转单词显示文本 -->
<h2>{{formatArr}}</h2>
</div>
<!-- 引入本地vue文件 -->
<script src="./lib/vue.js"></script>
<script>
// 创建app
const app = Vue.createApp({
data(){
return{
// message:"Hello Vue"
//1.姓名
firstName:"Kobe",
lastName:"bryant",
// 2.分数:根据分数显示及格/不及格
score:80,
// 2.一串文本:对文本中的单词进行反转显示
message:"my name is hdc"
}
},
methods:{
},
computed:{
// 计算属性默认对应的是一个函数
fullName(){return this.firstName + " " + this.lastName},
scoreLevel(){return this.score >= 60?"及格":"不及格"},
formatArr(){return this.message.split(" ").reverse().join(" ")},
}
})
// 挂载app
app.mount("#app")
计算属性vsmethods
计算属性的缓存
计算属性的setter和getter
认识侦听器watch
<div id="app">
<h2>{{message}}</h2>
<button @click="changeMessage">修改message</button>
</div>
<!-- 引入本地vue文件 -->
<script src="./lib/vue.js"></script>
<script>
// 创建app
const app = Vue.createApp({
data(){
return{
message:"Hello Vue",
info:{name:"hdc",age:21,height:1.88}
}
},
methods:{
changeMessage(){
this.message = "你好啊!WEBKing",
this.info={name:"kobe",age:30,height:1.98}
}
},
watch:{
// 可以传递两个参数:newValue/oldValue
message(newValue,oldValue){
console.log("message发生变化",newValue,oldValue)
},
// 对象类型拿到的都是proxy代理对象
info(newValue,oldValue){
console.log("info发生变化",newValue,oldValue)
// 获取原始对象
//方式一:展开运算符
console.log({...newValue},{...oldValue})
//Vue方法:toRaw()
console.log(Vue.toRaw(newValue),Vue.toRaw(oldValue))
}
}
})
// 挂载app
app.mount("#app")
侦听器watch的配置选项
◼ 我们先来看一个例子:
<div id="app">
<h2>{{info.name}}</h2>
<button @click="changeInfo">更改info</button>
</div>
<!-- 引入本地vue文件 -->
<script src="./lib/vue.js"></script>
<script>
// 创建app
const app = Vue.createApp({
data(){
return{
info:{name:"hdc",age:21}
}
},
methods:{
changeInfo(){
// 创建一个新对象赋值给info
// this.info = {name:"kobe"}
// 2,直接修改原对象某一个属性
this.info.name = "kobe"
}
},
watch:{
info(newValue,oldValue){
console.log("侦听到info发生改变",newValue,oldValue)
}
}
})
// 挂载app
app.mount("#app")
当我们点击按钮的时候会修改info.name的值;
这个时候我们使用watch来侦听info,可以侦听到吗?答案是不可以。
◼ 这是因为默认情况下,watch只是在侦听info的引用变化,对于内部属性的变化是不会做出响应的:
但是template模板里面的内容是深度监听的;
这个时候我们可以使用一个选项deep进行更深层的侦听;
注意前面我们说过watch里面侦听的属性对应的也可以是一个Object;
◼ 还有另外一个属性,是希望一开始的就会立即执行一次:
这个时候我们使用immediate选项;
这个时候无论后面数据是否有变化,侦听的函数都会有限执行一次;
watch:{
// 默认watch监听不会进行深度监听的
// info(newValue,oldValue){
// console.log("侦听到info发生改变",newValue,oldValue)
// }
// 进行深度监听
info:{
handler(newValue,oldValue){
console.log("侦听到info发生改变",newValue,oldValue)
// 没有改变info只是改变了info里的属性,所以他们两个是相等的
console.log(newValue === oldValue)//true
},
// 深度监听
deep:true,
// 第一次渲染的时候就执行监听器
immediate:true
}
}
侦听器watch的配置选项(代码)
侦听器watch的其他方式(一)
侦听器watch的其他方式(二)
◼ 另外一个是Vue3文档中没有提到的,但是Vue2文档中有提到的是侦听对象的属性:
```
'info.name':function(newValue,oldValue){
console.log(newValue,oldValue);
}
```
◼ 还有另外一种方式就是使用$watch 的API:
◼ 我们可以在created的生命周期(后续会讲到)中,使用this.$watch 来侦听;
第一个参数是要侦听的源;
第二个参数是侦听的回调函数callback;
第三个参数是额外的其他选项,比如deep、immediate;
```
// 生命周期回调函数:当前的组件被创建时自动执行
//一般在该函数中会进行网络请求
created(){
// this.message = []
this.$watch("message",(newValue,oldValue)=>{
console.log(newValue,oldValue)
},{deep:true,immediate:true})
}
})
```
标签:info,Vue,app,watch,newValue,API,oldValue,message,Options
From: https://www.cnblogs.com/hdc-web/p/18513660