Vue3中的计算属性和watch监视属性

1.computed函数

  • Vue2.xcomputed配置功能一致

代码展示:

  • Demo组件
    <template>
    <h1>一个人的信息</h1>
    姓:<input type="text" v-model="person.firstName">
    <br>
    名:<input type="text" v-model="person.lastName">
    <br>
    <span>全名:{{person.fullName}}</span>
    <br>
    全名:<input type="text" v-model="person.fullName">
    </template>

    <script>
    // Vue3中将计算属性变成了一个api(函数)
    import {reactive,computed} from 'vue'
    export default {
    name: 'Demo',
    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('-')//数组的split方法将收到的全名进行拆分
    person.firstName = nameArr[0]
    person.lastName = nameArr[1]
    }
    })

    //返回一个对象(常用)
    return {
    person
    }
    }
    }
    </script>

结果展示:

image

2.watch函数

  • Vue2.xwatch配置功能一致

  • 两个小“坑”:

    • 监视reactive定义的响应式数据时:oldValue无法正确获取、强制开启了深度监视(deep配置失效)。
    • 监视reactive定义的响应式数据中某个属性(切记是对象里面的某个属性)时:deep配置有效。

代码展示:

<template>
<h2>当前求和为:{{sum}}</h2>
<button @click="sum++">点我+1</button>
<hr>
<h2>当前的信息为:{{msg}}</h2>
<button @click="msg+='!'">修改信息</button>
<hr>
<h2>姓名:{{person.name}}</h2>
<h2>年龄:{{person.age}}</h2>
<h2>薪资:{{person.job.j1.salary}}K</h2>
<button @click="person.name+='~'">修改姓名</button>
<button @click="person.age++">增长年龄</button>
<button @click="person.job.j1.salary++">涨薪</button>
</template>

<script>
// Vue3中将监视属性变成了一个api(函数)
import {ref,reactive,watch} from 'vue'
export default {
name: 'Demo',
setup(){
//数据
let sum = ref(0)
let msg = ref('你好啊')
let person = reactive({
name:'张三',
age:18,
// 对象里面嵌套对象(深度监视)
job:{
j1:{
salary:20
}
}
})

//情况一:监视ref所定义的一个响应式数据(基本数据类型根本不需要deep)
watch(sum,(newValue,oldValue)=>{
console.log('sum变了',newValue,oldValue)
},{immediate:true})

//情况二:监视ref所定义的多个响应式数据(基本数据类型根本不需要deep)
watch([sum,msg],(newValue,oldValue)=>{
console.log('sum或msg变了',newValue,oldValue)
},{immediate:true})

/*
情况三:监视reactive所定义的一个响应式数据(对象)的全部属性
1.注意:此处无法正确的获取oldValue
2.注意:强制开启了深度监视(deep配置无效)
*/
watch(person,(newValue,oldValue)=>{
console.log('person变化了',newValue,oldValue)
},{deep:false}) //此处的deep配置无效

//情况四:监视reactive所定义的一个响应式数据(对象)中的某个属性
watch(()=>person.name,(newValue,oldValue)=>{
console.log('person的name变化了',newValue,oldValue)
})

//情况五:监视reactive所定义的一个响应式数据(对象)中的某些属性
watch([()=>person.name,()=>person.age],(newValue,oldValue)=>{
console.log('person的name或age变化了',newValue,oldValue)
})

//特殊情况(监视reactive所定义的一个响应式数据(对象)中的某个对象里面的某个属性)
watch(()=>person.job,(newValue,oldValue)=>{
console.log('person的job变化了',newValue,oldValue)
},{deep:true}) //此处由于监视的是reactive所定义的对象中的某个属性,所以deep配置有效


//返回一个对象(常用)
return {
sum,
msg,
person
}
}
}
</script>

结果展示:

image
image

3.watchEffect函数(非常的智能)

  • watch的套路是:既要指明监视的属性,也要指明监视的回调。

  • watchEffect的套路是:不用指明监视哪个属性,监视的回调中用到哪个属性,那就监视哪个属性(且相当于默认开启immediate)。

  • watchEffect有点像computed

    • computed注重的计算出来的值(回调函数的返回值),所以必须要写返回值。
    • watchEffect更注重的是过程(回调函数的函数体),所以不用写返回值。

代码展示:

<template>
<h2>当前求和为:{{sum}}</h2>
<button @click="sum++">点我+1</button>
<hr>
<h2>当前的信息为:{{msg}}</h2>
<button @click="msg+='!'">修改信息</button>
<hr>
<h2>姓名:{{person.name}}</h2>
<h2>年龄:{{person.age}}</h2>
<h2>薪资:{{person.job.j1.salary}}K</h2>
<button @click="person.name+='~'">修改姓名</button>
<button @click="person.age++">增长年龄</button>
<button @click="person.job.j1.salary++">涨薪</button>
</template>

<script>
// Vue3中将watchEffect变成了一个api(函数)
import {ref,reactive,watch,watchEffect} from 'vue'
export default {
name: 'Demo',
setup(){
//数据
let sum = ref(0)
let msg = ref('你好啊')
let person = reactive({
name:'张三',
age:18,
job:{
j1:{
salary:20
}
}
})

//监视属性
/* watch(sum,(newValue,oldValue)=>{
console.log('sum的值变化了',newValue,oldValue)
},{immediate:true}) */

watchEffect(()=>{//相较于watch更为智能
// 它能自动识别你在回调函数用到了'谁(属性或方法)',
//用到了谁就监视谁(并且它会开头调用一次,相当于默认开启immediate)
const x1 = sum.value
const x2 = person.job.j1.salary
console.log('watchEffect所指定的回调执行了,这里我监视了:sum.value和person.job.j1.salary')
})

//返回一个对象(常用)
return {
sum,
msg,
person
}
}
}
</script>

代码展示:

image