当前位置:首页 > VUE

vue组件watch实现原理

2026-01-22 21:32:27VUE

Vue 组件 watch 实现原理

Vue 的 watch 功能用于监听数据变化并执行回调函数。其核心原理基于 Vue 的响应式系统和依赖收集机制。

响应式系统基础

Vue 通过 Object.defineProperty(Vue 2)或 Proxy(Vue 3)实现数据劫持。当数据被访问时,依赖会被收集;当数据被修改时,依赖会被通知并触发更新。

watch 的工作流程

  1. 初始化监听
    在组件初始化阶段,Vue 会遍历 watch 选项中定义的属性,为每个属性创建一个 Watcher 实例。这个 Watcher 会记录回调函数和监听的目标路径。

  2. 依赖收集
    当首次执行 watch 时,会读取被监听属性的值,触发其 getter。此时,Watcher 会被添加到该属性的依赖列表中(即 Dep 实例的订阅者列表)。

  3. 触发回调
    当被监听的属性值发生变化时,会触发 setter,通知所有订阅该属性的 Watcher 执行更新。Watcher 会执行回调函数,并传入新值和旧值。

源码关键逻辑(Vue 2 示例)

// 简化版 Watcher 实现
class Watcher {
  constructor(vm, expOrFn, cb, options) {
    this.vm = vm;
    this.cb = cb;
    this.getter = parsePath(expOrFn); // 解析属性路径(如 'a.b.c')
    this.value = this.get(); // 触发依赖收集
  }

  get() {
    pushTarget(this); // 将当前 Watcher 设置为全局正在计算的 Watcher
    const value = this.getter.call(this.vm, this.vm); // 读取属性值,触发 getter
    popTarget(); // 恢复之前的 Watcher
    return value;
  }

  update() {
    const oldValue = this.value;
    this.value = this.get(); // 重新获取新值
    this.cb.call(this.vm, this.value, oldValue); // 执行回调
  }
}

深层监听与立即执行

  • deep: true
    递归遍历监听对象的所有子属性,为每个子属性绑定同样的依赖收集逻辑。
  • immediate: true
    在初始化时立即执行一次回调,此时旧值为 undefined

Vue 3 的优化

Vue 3 改用 Proxy 实现响应式,watch 通过 effectReactiveEffect 实现类似的依赖追踪,逻辑更简洁且性能更好。

vue组件watch实现原理

注意事项

  • 避免在回调中修改监听的数据,可能导致无限循环。
  • 对于复杂对象,使用 deep 监听可能带来性能开销,建议明确指定需要监听的子属性。

标签: 组件原理
分享给朋友:

相关文章

css制作图文混排原理

css制作图文混排原理

CSS 图文混排原理 图文混排主要通过 CSS 的浮动、定位、弹性布局或网格布局实现,核心是控制文本与图片的相对位置和环绕效果。 浮动(Float)实现环绕 使用 float 属性让图片浮动到左侧或…

实现vue组件

实现vue组件

创建 Vue 组件 Vue 组件可以通过单文件组件(.vue 文件)或直接在 JavaScript 中定义。以下是两种常见实现方式。 单文件组件方式 单文件组件包含模板、脚本和样式三部分,适合复杂项…

组件elementui

组件elementui

ElementUI 简介 ElementUI 是一套基于 Vue.js 的桌面端组件库,由饿了么前端团队开发并开源。它提供了丰富的 UI 组件(如按钮、表单、表格等),适合快速构建企业级中后台产品。…

vue实现水印组件

vue实现水印组件

Vue 水印组件的实现方法 使用Canvas绘制水印 在Vue组件中通过Canvas动态生成水印图案,将其作为背景添加到目标元素上。 <template> <div ref="…

react如何删除组件

react如何删除组件

删除 React 组件的几种方法 条件渲染法 通过状态控制组件是否渲染。当状态为 false 时,组件会被移除: const [showComponent, setShowComponent…

vue 组件实现 遮罩

vue 组件实现 遮罩

Vue 组件实现遮罩层的方法 基础遮罩层实现 创建一个简单的遮罩层组件,使用绝对定位覆盖整个视口。以下是一个基础实现: <template> <div class="mask"…