computed(计算属性)
模板内的表达式常用于简单的运算,当其过长或逻辑复杂,会难以维护,而计算属性就是用于解决该问题。
例如:
<div>
{{text.split(',').reverse().join(',')}}
</div>
上例表达式包含3个操作,并不是很清晰,所以在遇到复杂的逻辑时应该使用计算属性。
上例可以用计算属性进行改写:
<div id="app">
<h1>{{reversedText}}</h1>
</div>
<script>
new Vue({
el:'#app',
data: {
text:'123,456'
},
computed:{
reversedText:function(){
return this.text.split(',').reverse().join(',');
}
}
})
</script>
计算属性用法
在一个计算属性里可完成各种复杂的逻辑,包括运算、函数调用等,只要最终返回一个结果就可以了。除了上例简单的用法,计算属性还可以依赖多个Vue实例的数据,只要其中任一数据变化,计算属性就会重新执行,视图也会更新。
每一个计算属性都包含一个getter和一个setter,一般都是计算属性的默认用(getter)来读取。
例如,下面的实例展示的是在购物车内两个包裹的物品总结:
<div id="app">
<h1>{{prices}}</h1>
</div>
<script>
new Vue({
el:'#app',
data: {
packsge1:[
{
name:'HUAWEI Mate10',
price:4699,
count:2
},
{
name:'HUAWEI nove4',
price:2699,
count:1
}
],
packsge2:[
{
name:'apple',
price:3,
count:5
},
{
name:'banana',
price:2,
count:10
}
]
},
computed:{
prices:function(){
var prices=0;
for(var i=0;i<this.packsge1.length;i++){
prices+=this.packsge1[i].price*this.packsge1[i].count;
}
for(var i=0;i<this.packsge2.length;i++){
prices+=this.packsge2[i].price*this.packsge2[i].count;
}
return prices;
}
}
})
</script>
运行结果:
12132
当package1或package2中的商品有任何变化,比如购买数量或增删商品时,计算属性prices就会自动更新,视图中也会自动变化。
计算属性缓存
你可能会发现调用methods里的方法也可以与计算属性起到同样的作用,比如第一个实例可以用methods改写为:
<div id="app">
<h1>{{reversedText}}</h1>
</div>
<script>
new Vue({
el:'#app',
data: {
text:'123,456'
},
methods:{
reversedText:function(){
return this.text.split(',').reverse().join(',');
}
}
})
</script>
没有使用计算属性,在methods里定义一个方法实现相同的效果,甚至该方法还可结受参数,使用起来更灵活,那为啥还需要计算属性呢?
原因就是计算属性是基于它的依赖缓存的,一个计算属性所依赖的数据发生变化时,它才会重新取值,所以只要text不改变,计算属性也就不更新。例如:
computed:{
now:function(){
return Date.now()
}
}
这里的Date.now()不是响应式依赖,所以计算属性now不会更新。但是methods不同,只要中新渲染,它就会调用,因此函数也会被执行。
使用计算属性还是methods取决于你是否需要缓存,当遍历大数组和大量计算时,应当使用计算属性,除非你不希望得到缓存。