vue2原理

20 阅读1分钟
  1. 初始化阶段:Vue 会遍历 data 中的所有属性,使用Object.defineProperty为每个属性添加 getter 和 setter。

  2. 依赖收集阶段

    • 当视图渲染时,会读取 data 中的属性,触发 getter 方法
    • getter 方法会把当前的 Watcher(可以理解为视图的更新器)添加到该属性的依赖收集器(subs 数组)中
  3. 数据更新阶段

    • 当修改 data 中的属性时,会触发 setter 方法
    • setter 方法会通知依赖收集器中的所有 Watcher
    • 每个 Watcher 会触发对应的视图更新

这个机制让 Vue 实现了 "数据驱动视图" 的核心特性,开发者只需要关注数据变化,而不必手动操作 DOM。

如果用简单的代码来模拟这个过程,大概是这样的:

javascript

运行

// 模拟依赖收集器
class Dep {
  constructor() {
    this.subs = []; // 存储依赖
  }
  
  // 添加依赖
  depend() {
    if (window.target) {
      this.subs.push(window.target);
    }
  }
  
  // 通知更新
  notify() {
    this.subs.forEach(sub => sub.update());
  }
}

// 模拟Watcher
class Watcher {
  constructor(updateFn) {
    this.updateFn = updateFn;
    window.target = this; // 将当前watcher设置为全局目标
  }
  
  // 执行更新
  update() {
    this.updateFn();
  }
}

// 模拟响应式处理
function defineReactive(obj, key, val) {
  const dep = new Dep(); // 每个属性有一个依赖收集器
  
  Object.defineProperty(obj, key, {
    get() {
      dep.depend(); // 收集依赖
      return val;
    },
    set(newVal) {
      if (newVal !== val) {
        val = newVal;
        dep.notify(); // 通知更新
      }
    }
  });
}

这个简化的模型展示了 Vue 响应式系统的核心思想,实际的 Vue 实现会更复杂,但基本原理是一致的。