Vue 监听器和计算属性到底有什么不同?
各自的适用场景
计算属性临时快照
官方文档对于计算属性提到了一个重要的点子——“临时快照”(可能就是前面说的计算属性缓存),每当源状态发生变化时,就会创建一个新的快照。
有时候创建快照是没有意义的,对于间隔时间很短的源数据修改,比如输入框输入时页面上的一些变化。输入第一个字符到第二个字符之间的间隔时间,字符有长有短,每一次都要创建“临时快照”,这样是没有意义的,反而可能增加开销。
计算属性除了可以用于复杂的模板取值计算(普通函数也可以做,也不是它的特性),还可以计算一次而在页面上多次使用(这是计算属性的“临时快照”的优势)。
监听器的副作用
因此,上面说到的情况就更加适合用监听器来做,监听器不创建“临时快照”。监听器更适用于官方文档说的场景:“我们需要在状态变化时执行一些‘副作用’:例如更改 DOM,或是根据异步操作的结果去修改另一处的状态”。
监听器的副作用就是被监测的数据源发生变化才被触发,而不能被其他数据源发生变化而受到影响。具体往下看,就是我说的监听器单一性。
深入思考两者区别
计算属性由于在计算过程中依赖了很多响应式数据,一旦某一个响应式数据发生变化,那么整个计算属性都将重新计算。我就自以为计算属性有共享性。
虽然监听器也可以依赖于很多响应式数据,但是监听器只负责一个数据源,而被依赖的其他响应式数据一旦发生变化,都无法触发这个监听器,即监听器的单一性。
监听器:单一性
Talk is cheap. Show me the code.
定义两个输入框需要绑定的响应式数据 input
、copyInput
,监听器只负责监听 input,当监听器被触发时,新的值将赋值给 input,并且 input 也拼接给 copyInput(这里为了让两个产生联系而设计的无脑代码):
let input = ref("");
let copyInput = ref("");
watch(input, (newVal, oldVal) => {
input.value = newVal;
copyInput.value += input.value;
console.log("input value has changed.");
});
输入框绑定响应式数据,页面展示 copyInput:
<div class="demo1">
<div>CopyInput Value: {{ copyInput }}</div>
<div>
<span>Input: </span>
<input v-model="input" />
</div>
<div>
<span>CopyInput: </span>
<input v-model="copyInput" />
</div>
</div>
第一个输入框内(即绑定 input 的输入框)输入三次,监听器被触发 3 次,当第二个输入框的数据发生变化时,控制台不打印,也就是说,监听器里面被依赖的数据没有因为改变而被触发。
计算属性:共享性
计算属性里面被依赖的其中一个响应式数据发生了变化,整个计算属性都将被重新计算。那么,计算属性是否和上面提到的监听器一样呢?
let input = ref("");
let copyInput = ref("");
const result = computed(() => {
console.log("computed has changed.");
return (copyInput.value += input.value);
});
<div class="demo2">
<div>CopyInput Value Result: {{ result }}</div>
<div>
<span>Input: </span>
<input v-model="input" />
</div>
<div>
<span>CopyInput: </span>
<input v-model="copyInput" />
</div>
</div>
不管我改哪一个,只要是被计算属性依赖的数据源发生改变,这个计算属性都被触发,即共享性:
总结
(1)计算属性适合数据源发生变化间隔长,且页面使用它的次数多的情况;监听器适合数据源发生变化间隔短,或有异步操作,或有副作用的情况。
(2)如果不想其他响应式数据发生变化而导致被监测的源数据发生变化,那么就使用监听器。如果其他响应式数据发生变化,而被监测的源数据也一同发生变化,那么就使用计算属性。
声明
文章中所说的计算属性具有共享性和监听器具有单一性是为了方便理解他们之间的不同,博主擅自给的定义,可能存在不严谨的地方。
- 计算属性具有共享性:指的是计算属性里面的被依赖的响应式数据只要有一个发生变化,整一个计算属性都重新计算,牵一发而动全身。
- 监听器具有单一性:指的是监听器只负责它监听的那个数据源,如果发生变化,才会被触发,如果里面被依赖的其他数据源发生变化时,这个监听器不会被触发。
以上证明了我所阐述的观点,如果你有收货,请给我点个赞+收藏吧!
Vue 监听器和计算属性到底有什么不同?的更多相关文章
- vue监听器watch & 计算属性computed
侦听器watch vue中watch是用来监听vue实例中的数据变化 watch监听时有几个属性: handle:其值是一个回调函数,就是监听对象对话的时候需要执行的函数 deep:其值true 或者 ...
- Vue的computed计算属性是如何实现的
一个开始 有如下代码,full是一个计算属性,开始,他的值是'hello world',1s后,msg变成了‘I like’, full的值同步变成了'I like world';其原理解析来看一下. ...
- Vue学习之vue中的计算属性和侦听器
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...
- Vue(基础三)_监听器与计算属性
一.前言 本文主要涉及: 1.watch()监听单个属性 2.computed可以监听多个属性 3.点击li标签切换音乐案例 二.主要内容 1.watch()监听器(监听单一数据) (1)监听 ...
- Vue中的计算属性和监听器(computed 与 watch)
react中数据是单向绑定的,而vue中数据是双向绑定的.为什么? 在react中,主要是通过setState 去改变state的值:而在vue中,会自动的触发set 与get 改变属性的值. 在vu ...
- Vue基础之计算属性
适用场景 设想一个场景,你需要得到一个复杂运算/逻辑的返回值,利用模板内的表达又过长且难以阅读和维护,这时计算属性就可以很好的解决你的问题.看下面的例子: <!DOCTYPE html> ...
- 关于vue.js的计算属性练习代码
参照官网联系如下: <!DOCTYPE html><html lang="en"><head> <meta charset="U ...
- Vue 过滤器与计算属性
过滤器 V1.x 版本 过滤器基础 过滤器是一个通过输入数据,能够及时对数据进行处理并返回一个数据结果的简单函数.Vue有很多很便利的过滤器,可以参考官方文档,http://cn.vuejs.org/ ...
- vue学习笔记 计算属性(四)
计算属性就是vue实例里的computed属性,对应一个对象,里面可以放各种方法,方法的作用就是可以生成和数据变量对应的计算后的变量,跟数据相关的复杂逻辑变量,都可以使用计算属性实现,computed ...
随机推荐
- 点亮Arduino内置的LED灯
更新记录 2022年4月16日:本文迁移自Panda666原博客,原发布时间:2021年9月3日. 15块软妹币的板子镇楼. 上一篇配置好了开发环境,然后就开始搞第一个小灯的实验了. 原理相当的简单, ...
- 8.shell编程之免交互
shell编程之免交互 目录 shell编程之免交互 Here Document免交互 免交互定义 Here Document变量设定 多行的注释 expect expect 定义 expect基本命 ...
- Spring Security:用户和Spring应用之间的安全屏障
摘要:Spring Security是一个安全框架,作为Spring家族的一员. 本文分享自华为云社区<[云驻共创]深入浅出Spring Security>,作者:香菜聊游戏. 一.前言 ...
- 【问题解决】Alpine镜像中执行jstack、arthas等命令提示Unable to get pid of LinuxThreads manager thread
问题现象 最近在处理项目上问题发现之前同事构建的AlpineLinux的镜像不能执行jstack等JDK命令,报错如下. Unable to get pid of LinuxThreads manag ...
- Pytorch Dataloader加速
在进行多卡训练的时候,经常会出现GPU利用率上不来的情况,无法发挥硬件的最大实力. 造成这种现象最有可能的原因是,CPU生成数据的能力,已经跟不上GPU处理数据的能力. 方法一 常见的方法为修改Dat ...
- C#《原CSharp》第三回 万文疑谋生思绪 璃月港口见清玉
第三回 万文疑谋生思绪 璃月港口见清玉 ===================================================================== 云溪愣了下,在他的认 ...
- 集合-list常用方法总结
每个方法使用见下方代码详解 点击查看代码 ArrayList list = new ArrayList(); list.add("AA"); list.add(123); list ...
- 微信小程序使用echarts/数据刷新重新渲染/图层遮挡问题
1.微信小程序使用echarts,首先下载echarts并导入小程序项目中,因小程序后期上线对文件大小有要求,所以建议进行定制下载导入可减少文件大小占比,也可以下载以前旧版本文件比较小的应付使用 下载 ...
- python中print函数
python中的输出函数 注意不是C中的printf 起作用就是将希望输出的内容输出在IDLE或标准的控制台上 python解释器将代码翻译成及其能听懂的语言,从而实现代码的实现 print的输出内容 ...
- 循环数组%操作下的一些解释(对于4.4UVA133的一些解释)
1.循环数组一般不推荐通过建立相同的数组不断叠加来实现,虽然理论上是可行的,但是会浪费极大的空间,特别是对于大数据的情况下,程序一般会马上挂掉 2.循环数组的结构表示中的一种常用形式就是通过取余操作来 ...