问题
今天在维护之前同事的旧项目时,发现一处搜索功能不能实现,原因是同事在判断逻辑中将计算属性的值赋给了data中的变量,希望search内容更改时能够更新计算属性。
这就衍生出了两个问题
- 为何计算属性的方法只在第一次赋值时调用了
- 为何计算属性的方法触发后data内的值仍旧未发生改变
在进入正题之前,我们先来复习一下吧
计算属性使用方法
template
<p>Has published books:</p>
<span>{{ publishedBooksMessage }}</span>
js
export default {
data() {
return {
author: {
name: 'John Doe',
books: [
'Vue 2 - Advanced Guide',
'Vue 3 - Basic Guide',
'Vue 4 - The Mystery'
]
}
}
},
computed: {
// 一个计算属性的 getter
publishedBooksMessage() {
// `this` 指向当前组件实例
return this.author.books.length > 0 ? 'Yes' : 'No'
}
}
}
带有get、set方法
export default {
data() {
return {
firstName: 'John',
lastName: 'Doe'
}
},
computed: {
fullName: {
// getter
get() {
return this.firstName + ' ' + this.lastName
},
// setter
set(newValue) {
// 注意:我们这里使用的是解构赋值语法
[this.firstName, this.lastName] = newValue.split(' ')
}
}
}
}
计算属性知识点:
-
写在computed对象中的属性,本质上是一个方法,不过使用时依旧当属性来使用
-
计算属性和data属性都是变量-不能重名. 用法和data相同
-
想要给计算属性赋值, 需要使用set方法
-
虽然模板语法使用非常便利,但是它是被设计成用于简单运算的。在模板中放入太多的逻辑会让模板过重且难以维护,此时可以使用计算属性
-
因为计算属性是基于缓存实现的,只在计算属性所依赖的数据发生改变时它们才会重新求值,否则访问 计算属性会立即返回之前的计算结果,而不必再次执行函数。 相比之下,每当触发重新渲染时,调用方法将总会再次执行函数,因此相比于函数,在需要运算求得结果时可以优先考虑计算属性
-
在js中执行计算属性赋值,并不能让被赋值的属性成为计算属性,因为js中的计算属性赋值其实是相当于执行了计算属性的方法,获得他的返回值而已,返回值每次在计算属性中执行时都会重新生成,自然也不存在浅拷贝使双方数据同步的说法。
-
计算属性本身必须被template模板应用才会在引用值更新时触发方法
答案
答案就在6、7两条
-
在js中执行计算属性赋值,并不能让被赋值的属性成为计算属性,因为js中的计算属性赋值其实是相当于执行了计算属性的方法,获得他的返回值而已,返回值每次在计算属性中执行时都会重新生成,自然也不存在浅拷贝使双方数据同步的说法。
-
计算属性本身必须被template模板应用才会在引用值更新时触发方法