Vue 3 第八章:Watch侦听器
文章目录
- Watch侦听器
- 1. 基础概念
- 1.1. Watch的基本用法
- 例子1:监听单个`ref`的值,直接监听
- 例子2:监听多个`ref`的值,采用数组形式
- 例子3:深度监听
- 例子4:监听`reactive`响应式对象单一属性,采用`回调函数`的形式
- 2. Watch的高级用法
- 2.1. immediate
- 2.2. deep
- 2.3. flush
- 3. Watch的性能优化
- 3.1. 使用computed代替watch
- 3.2. 使用throttle和debounce控制回调函数的执行频率
- 总结
Watch侦听器
在Vue3中,watch特性进行了一些改变和优化。与computed不同,watch通常用于监听数据的变化,并执行一些副作用,例如发送网络请求、更新DOM等。本文将介绍Vue3中watch特性。
1. 基础概念
1.1. Watch的基本用法
watch(source, callback, options?)
其中,source表示要监听的数据,可以是一个响应式的数据对象、一个计算属性或一个方法的返回值;callback表示当数据发生变化时要执行的回调函数;options表示watch的一些配置选项,例如immediate、deep、flush等。
例子1:监听单个ref的值,直接监听
<template><div><!-- 侦听单个变量 -->case1:<input v-model="userName" type="text"></div>
</template><script setup lang="ts">
import { ref, watch } from 'vue';const userName= ref<string>('张三');watch(userName, (newVal, oldVal) => {console.log(newVal, oldVal);
})
</script>
例子2:监听多个ref的值,采用数组形式
<template><div><!-- 侦听多个变量 -->case1:<input v-model="userName" type="text">case2:<input v-model="age" type="text"></div>
</template><script setup lang="ts">
import { ref, watch } from 'vue';const userName= ref<string>('张三');
const age= ref<number>(18);watch([userName, age], (newVal, oldVal) => {console.log(newVal, oldVal);
})
</script>
例子3:深度监听
- 如果用
ref实现深层次对象的响应式,侦听的时候需要开启深度侦听 - 用
reactive实现响应式,开启deep和不开启deep效果是一样的
<template><div><!-- 深度侦听 -->case1:<input v-model="obj.foo.bar.name" type="text"></div>
</template><script setup lang="ts">
import { reactive, watch } from 'vue';const obj = reactive({foo: {bar: {name: '张三'}}
})
watch(obj, (newVal, oldVal) => {console.log(newVal, oldVal);
}, {// deep: true, // 深度侦听, 监听ref创建的响应式对象必须开启
})
</script>
注意:此处监听的新值和旧值相同,主要是因为新旧值引用地址是相同的,此处可采取computed计算属性先实现深拷贝。示例如下:
import { reactive, watch, computed } from 'vue';const obj = reactive({foo: {bar: {name: '张三'}}
})let obj1 = reactive({})obj1 = computed(() => {return JSON.parse(JSON.stringify(obj))
})watch(obj1, (newVal, oldVal) => {console.log(newVal, oldVal);
})
例子4:监听reactive响应式对象单一属性,采用回调函数的形式
<template><div><!-- 侦听单一属性 -->case1:<input v-model="obj.foo.bar.name" type="text"></div>
</template><script setup lang="ts">
import { reactive, watch } from 'vue';const obj = reactive({foo: {bar: {name: '张三'}}
})
watch(() => obj.foo.bar.name, (newVal, oldVal) => {console.log(newVal, oldVal);}
)
</script>
2. Watch的高级用法
在Vue3中,watch特性进行了一些改变和优化。除了基本的watch用法外,还有一些高级用法可以使watch更加灵活和方便。下面是几个常用的高级用法:
2.1. immediate
immediate选项可以用于指定watch在组件创建时立即执行一次回调函数,而不必等待数据的变化。例如:
import { reactive, watch } from 'vue'const state = reactive({count: 0
})watch(() => state.count,(newVal, oldVal) => {console.log(`count值从${oldVal}变成了${newVal}`)},{ immediate: true }
)
在上面的例子中,我们使用immediate选项将watch的回调函数在组件创建时立即执行了一次,输出了初始值。当state.count变化时,watch的回调函数还会被再次执行。
2.2. deep
deep选项可以用于深度监听一个对象或数组的变化。当我们监听一个对象或数组时,默认情况下只会监听对象或数组的引用变化,而不会监听其内部数据的变化。如果我们需要深度监听对象或数组内部数据的变化,可以使用deep选项。例如:
import { reactive, watch } from 'vue'const state = reactive({todos: [{ id: 1, text: '学习Vue3', done: false },{ id: 2, text: '学习React', done: false },{ id: 3, text: '学习Angular', done: true }]
})watch(() => state.todos,(newVal, oldVal) => {console.log(`todos数组发生了变化`)},{ deep: true }
)state.todos[0].done = true // 输出:todos数组发生了变化
注意:当我们使用deep选项时,watch的性能会受到一定的影响,因为Vue需要对对象或数组进行递归遍历。因此,只有在必要的情况下才应该使用deep选项。
2.3. flush
flush选项可以用于指定watch的回调函数在何时执行。例如:
- sync:同步模式下执行
- pre:在数据变化之前执行回调函数
- post:在数据变化之后执行回调函数,但是需要等待所有依赖项都更新后才执行
import { reactive, watch } from 'vue'const state = reactive({count: 0
})watch(() => state.count,(newVal, oldVal) => {console.log(`count值从${oldVal}变成了${newVal}`)},{ flush: 'sync' }
)state.count++ // 输出:count值从0变成了1
在上面的例子中,我们使用flush选项将watch的回调函数在同步模式下执行了,这意味着watch的回调函数会在数据变化之后立即执行。当我们执行state.count++时,会触发count的变化,从而执行watch的回调函数并输出变化的值。
3. Watch的性能优化
在使用watch时,为了优化性能,我们可以采取以下一些方法:
3.1. 使用computed代替watch
在有些情况下,如果我们只是想监听一个值的变化,并在变化时执行一些操作,我们可以使用computed代替watch。computed可以自动缓存计算的结果,只有在它的依赖项变化时才会重新计算,因此可以提高一定的性能。例如:
import { reactive, computed } from 'vue'const state = reactive({count: 0
})const doubleCount = computed(() => {return state.count * 2
})console.log(doubleCount.value) // 输出:0state.count++console.log(doubleCount.value) // 输出:2
3.2. 使用throttle和debounce控制回调函数的执行频率
在有些情况下,我们可能会频繁地监听一个值的变化,并在变化时执行一些操作。如果回调函数执行的太频繁,会影响性能。为了避免这种情况,我们可以使用throttle和debounce控制回调函数的执行频率。
throttle和debounce都是用于控制函数执行频率的工具函数。throttle可以用于控制函数在一定时间内只能执行一次,而debounce可以用于控制函数在一定时间内不会连续执行。例如:
import { reactive, watch } from 'vue'
import { throttle } from 'lodash-es'const state = reactive({count: 0
})watch(() => state.count,throttle((newVal, oldVal) => {console.log(`count值从${oldVal}变成了${newVal}`)}, 1000)
)state.count++
总结
watch特性是Vue中非常重要的一个特性,通过学习watch的基础概念、高级用法、实战应用和性能优化方法,可以帮助我们更好地理解和应用Vue。
相关文章:
Vue 3 第八章:Watch侦听器
文章目录Watch侦听器1. 基础概念1.1. Watch的基本用法例子1:监听单个ref的值,直接监听例子2:监听多个ref的值,采用数组形式例子3:深度监听例子4:监听reactive响应式对象单一属性,采用回调函数的…...
GlassFish的安装与使用
一、产品下载与安装glassfish下载地址:https://download.oracle.com/glassfish/5.0.1/release/index.html下载后解压即完成安装,主要目录说明:bin目录:为asadmin命令所在目录。glassfish为主目录:glassfish\bin目录为命…...
【java】Java 重写(Override)与重载(Overload)
文章目录重写(Override)方法的重写规则Super 关键字的使用重载(Overload)重载规则实例重写与重载之间的区别总结重写(Override) 重写是子类对父类的允许访问的方法的实现过程进行重新编写, 返回值和形参都不能改变。即外壳不变,核心重写! 重写的好处在于…...
OpenCV-PyQT项目实战(12)项目案例08:多线程视频播放
欢迎关注『OpenCV-PyQT项目实战 Youcans』系列,持续更新中 OpenCV-PyQT项目实战(1)安装与环境配置 OpenCV-PyQT项目实战(2)QtDesigner 和 PyUIC 快速入门 OpenCV-PyQT项目实战(3)信号与槽机制 …...
面向对象设计模式:结构型模式之装饰器模式
文章目录一、引入二、装饰器模式2.1 Intent 意图2.2 Applicability 适用性2.3 类图2.4 优缺点2.5 应用实例:Java IO 类2.6 应用实例:咖啡馆订购系统一、引入 咖啡馆订购系统 Initial 初始 4 种咖啡 House blend (混合咖啡)Dark Roast (深度烘培)Decaf (…...
Unity iOS 无服务器做一个排行榜 GameCenter
排行榜需求解决方案一(嗯目前只有一)UnityEngine.SocialPlatformsiOS GameCenterAppStoreConnect配置Unity 调用(如果使用GameCenter系统的面板,看到这里就可以了)坑(需要获取数据做自定义面板的看这里)iOS代码Unity 代码吐槽需求 需求:接入…...
现在招个会自动化测试的人是真难呀~你会个锤子的自动化测试
现在招个会自动化测试的人是真难呀~ 前一段时间公司计划要招2个自动化测试到岗,同事面试了十几个来应聘的人,发现一个很奇怪的现象,在面试的时候,如果问的是框架API、脚本编写这些问题,基本上所有人都能对答如流&…...
OracleDatabase——数据库表空间dmp导出与导入
由于公司的程序一直部署在客户现场内网,内网调试难度高,一般是有备份还原数据库的需求,这里简记备份(导出)数据库dmp文件与恢复(导入)的步骤。 一、导出dmp文件 exp与expdp命令异同 相同点&a…...
20张图带你彻底了解ReentrantLock加锁解锁的原理
哈喽大家好,我是阿Q。 最近是上班忙项目,下班带娃,忙的不可开交,连摸鱼的时间都没有了。今天趁假期用图解的方式从源码角度给大家说一下ReentrantLock加锁解锁的全过程。系好安全带,发车了。 简单使用 在聊它的源码…...
Dockerfile构建Springboot镜像
Dockerfile构建Springboot镜像 文章目录 Dockerfile构建Springboot镜像 简介实例演示 前期准备 Docker环境Springboot项目Dockerfile文件 Windows 要求构建镜像启动测试 Linux 要求构建镜像启动测试 简介 容器技术大流行的时代,也是docker大流行的时代。 此文…...
从深分页查询到覆盖索引
最近看到一道面试题,如何优化深分页查询 最简单的例子是 select * from web_bill_main limit 30000,10;分页达到30000行,需要把前面29999行都过滤掉,才能找到这10条数据 所以整体时间花了80ms(工具显示时间) 我当时的第一反应是࿰…...
Go语言学习的第三天--下部分(Gin框架的基础了解)
每天都会分享Go的知识,喜欢的朋友关注一下。每天的学习分成两部分基础(必要的,基础不牢地动山摇),另一部分是Go的一些框架知识(会不定时发布,因为小Wei也是一名搬砖人)。但是可以保证…...
JDK的动态代理(powernode 文档)(内含源代码)
JDK的动态代理(powernode 文档)(内含源代码) 源代码下载链接地址:https://download.csdn.net/download/weixin_46411355/87546086 一、动态代理 目录JDK的动态代理(powernode 文档)࿰…...
第1章 多线程基础
第1章 多线程基础 1.1.2 线程与进程的关系 进程可以看成是线程的容器,而线程又可以看成是进程中的执行路径。 1.2 多线程启动 线程有两种启动方式:实现Runnable接口;继承Thread类并重写run()方法。 执行进程中的任务时才会产生线程&a…...
Linux基本指令(一)
文章目录文件操作文档操作系统管理网络通信备份压缩Ctrl Alt T 打开终端 文件操作 1.复制文件 cp afile bfile (将名为afile的文件复制到名为bfile的文件夹中,如果bfile文件不存在,系统将会创建此文件,如果bfile文件已经存在&a…...
el-dialog子组件在mounted周期内获取不到dom?
el-dialog子组件在mounted周期内获取不到dom?一、问题描述二、分析原因三、猜测正常父子组件在mounted生命周期内可以获得dom 父created—子created—子mounted—父mounted----子updated—父updated 一、问题描述 ** el-dialog控制显示隐藏是css控制的display&…...
第九章 opengl之光照(光照贴图)
OpenGL光照贴图漫反射贴图镜面光贴图光照贴图 一个物体的不同部分是不同的材质,那么会有不同的环境光和漫反射颜色表现。 漫反射贴图 原理就是:纹理。 是对同样的原理使用了不同的名字:其实都是使用一张覆盖物体的图像,让我们能…...
JDK动态代理(powernode CD2207 video)(内含教学视频+源代码)
JDK动态代理(powernode CD2207 video)(内含教学视频源代码) 教学视频原代码下载链接地址:https://download.csdn.net/download/weixin_46411355/87545977 目录JDK动态代理(powernode CD2207 video…...
【Linux】Sudo的隐晦bug引发的一次业务问题排查
Sudo的隐晦bug引发的一次业务问题排查写在前面问题描述问题排查高负载现象排查日志排查跟踪任务调度过程Sudo引发的问题手动复现问题分析处理方案写在前面 记录一次生产环境sudo启动进程频繁被Kill且不报错的异常处理过程,如果遇到同样的问题只想要解决方案&#x…...
Java VisualVM 安装 Visual GC 插件图文教程
文章目录1. 通过运行打开 Java VisualVM 监控工具2. 菜单栏初始视图说明3. 工具插件菜单说明4. 手工安装插件5. 重启监控工具查看 Visual GC1. 通过运行打开 Java VisualVM 监控工具 首先确保已安装 Java 环境,如此处安装版本 JDK 1.8.0_161 C:\Users\niaonao>j…...
变量 varablie 声明- Rust 变量 let mut 声明与 C/C++ 变量声明对比分析
一、变量声明设计:let 与 mut 的哲学解析 Rust 采用 let 声明变量并通过 mut 显式标记可变性,这种设计体现了语言的核心哲学。以下是深度解析: 1.1 设计理念剖析 安全优先原则:默认不可变强制开发者明确声明意图 let x 5; …...
大数据学习栈记——Neo4j的安装与使用
本文介绍图数据库Neofj的安装与使用,操作系统:Ubuntu24.04,Neofj版本:2025.04.0。 Apt安装 Neofj可以进行官网安装:Neo4j Deployment Center - Graph Database & Analytics 我这里安装是添加软件源的方法 最新版…...
应用升级/灾备测试时使用guarantee 闪回点迅速回退
1.场景 应用要升级,当升级失败时,数据库回退到升级前. 要测试系统,测试完成后,数据库要回退到测试前。 相对于RMAN恢复需要很长时间, 数据库闪回只需要几分钟。 2.技术实现 数据库设置 2个db_recovery参数 创建guarantee闪回点,不需要开启数据库闪回。…...
label-studio的使用教程(导入本地路径)
文章目录 1. 准备环境2. 脚本启动2.1 Windows2.2 Linux 3. 安装label-studio机器学习后端3.1 pip安装(推荐)3.2 GitHub仓库安装 4. 后端配置4.1 yolo环境4.2 引入后端模型4.3 修改脚本4.4 启动后端 5. 标注工程5.1 创建工程5.2 配置图片路径5.3 配置工程类型标签5.4 配置模型5.…...
CVPR 2025 MIMO: 支持视觉指代和像素grounding 的医学视觉语言模型
CVPR 2025 | MIMO:支持视觉指代和像素对齐的医学视觉语言模型 论文信息 标题:MIMO: A medical vision language model with visual referring multimodal input and pixel grounding multimodal output作者:Yanyuan Chen, Dexuan Xu, Yu Hu…...
云计算——弹性云计算器(ECS)
弹性云服务器:ECS 概述 云计算重构了ICT系统,云计算平台厂商推出使得厂家能够主要关注应用管理而非平台管理的云平台,包含如下主要概念。 ECS(Elastic Cloud Server):即弹性云服务器,是云计算…...
Qt/C++开发监控GB28181系统/取流协议/同时支持udp/tcp被动/tcp主动
一、前言说明 在2011版本的gb28181协议中,拉取视频流只要求udp方式,从2016开始要求新增支持tcp被动和tcp主动两种方式,udp理论上会丢包的,所以实际使用过程可能会出现画面花屏的情况,而tcp肯定不丢包,起码…...
2025年能源电力系统与流体力学国际会议 (EPSFD 2025)
2025年能源电力系统与流体力学国际会议(EPSFD 2025)将于本年度在美丽的杭州盛大召开。作为全球能源、电力系统以及流体力学领域的顶级盛会,EPSFD 2025旨在为来自世界各地的科学家、工程师和研究人员提供一个展示最新研究成果、分享实践经验及…...
阿里云ACP云计算备考笔记 (5)——弹性伸缩
目录 第一章 概述 第二章 弹性伸缩简介 1、弹性伸缩 2、垂直伸缩 3、优势 4、应用场景 ① 无规律的业务量波动 ② 有规律的业务量波动 ③ 无明显业务量波动 ④ 混合型业务 ⑤ 消息通知 ⑥ 生命周期挂钩 ⑦ 自定义方式 ⑧ 滚的升级 5、使用限制 第三章 主要定义 …...
uni-app学习笔记二十二---使用vite.config.js全局导入常用依赖
在前面的练习中,每个页面需要使用ref,onShow等生命周期钩子函数时都需要像下面这样导入 import {onMounted, ref} from "vue" 如果不想每个页面都导入,需要使用node.js命令npm安装unplugin-auto-import npm install unplugin-au…...
