Vue 2 的 watch
选项用于监听组件中数据的变化,并在变化时执行相应的操作。它的用法分为"对象写法"和"数组写法",还可以配置深度监听、立即执行等选项。下面按常见场景逐一说明。
1. 基本用法(函数写法)
监听单个数据属性,最简单、最常用的形式:
js
export default {
data() {
return {
msg: 'hello'
}
},
watch: {
// 监听 msg 的变化
msg(newVal, oldVal) {
console.log('msg 变化:', oldVal, '→', newVal)
}
}
}
2. 对象写法(带选项)
当需要配置 immediate
、deep
等高级选项时使用:
js
export default {
data() {
return {
user: { name: 'Tom', age: 18 }
}
},
watch: {
user: {
handler(newVal, oldVal) {
console.log('user 对象变化:', newVal)
},
deep: true, // 深度监听对象内部属性变化
immediate: true // 组件创建后立即执行一次 handler
}
}
}
3. 监听对象的某个具体属性
监听嵌套对象中的某个字段,用字符串路径:
js
export default {
data() {
return {
user: { name: 'Tom', age: 18 }
}
},
watch: {
// 监听 user.name
'user.name'(newVal, oldVal) {
console.log('user.name 变化:', newVal)
}
}
}
4. 数组写法(同时监听多个字段)
当多个字段共享同一个回调时,可以用数组:
js
export default {
data() {
return {
a: 1,
b: 2
}
},
watch: {
// a 或 b 任一变化都会触发
a: 'someMethod',
b: 'someMethod'
},
methods: {
someMethod() {
console.log('a 或 b 变化了')
}
}
}
5. 使用 $watch
在运行时动态监听
有时需要在 created
或 mounted
钩子里根据条件动态监听:
js
export default {
data() {
return { count: 0 }
},
created() {
this.$watch(
() => this.count,
(newVal, oldVal) => {
console.log('count 变化:', newVal)
},
{ immediate: true }
)
}
}
6. 常见配置项
选项 | 说明 |
---|---|
deep |
是否深度监听对象或数组内部变化(默认 false )。 |
immediate |
是否在监听开始后立即执行一次 handler (默认 false )。 |
flush |
控制回调触发时机(Vue2 内部使用较少,Vue3 更常用)。 |
7. 注意事项
- 性能 :开启
deep: true
会递归遍历对象,开销较大,尽量避免监听大对象。 - 数组/对象替换:直接替换整个数组或对象引用(而非修改内部元素)总能被监听到。
- 数组索引/长度 :直接通过索引修改数组元素
arr[0] = newVal
不会被检测到,应使用Vue.set
或this.$set
。
8. 完整示例
vue
<template>
<div>
<input v-model="user.name" />
<p>姓名:{{ user.name }}</p>
</div>
</template>
<script>
export default {
data() {
return {
user: { name: 'Tom' }
}
},
watch: {
'user.name': {
handler(newVal, oldVal) {
console.log(`姓名从 ${oldVal} 改为 ${newVal}`)
},
immediate: true
}
}
}
</script>
以上覆盖了 Vue 2 中 watch
的绝大多数日常用法,根据场景选择合适的形式即可。