怎么在控制台打印vue实例对象_深入Vue响应式原理,实现一个简易版Vue

本文详细介绍了Vue的响应式原理,包括数据驱动、数据响应式的核心原理(Vue2和Vue3)、发布订阅模式和观察者模式。通过对Vue实例对象的分析,探讨了Observer、Compiler、Dep和Watcher的角色及其工作方式,逐步实现了一个简易版的Vue,重点讲解了双向绑定的实现。
摘要由CSDN通过智能技术生成

49eb2c8288032764e7290a1a8db83742.png

来自拉勾教育大前端训练营 vue 框架源码与进阶模块,以下内容为个人在学习过程中对响应式原理的总结~

先实现 mini 版 Vue 之前,我们先来了解一些概念

1、数据驱动

  • 数据驱动
  • 响应式的核心原理
  • 发布订阅模式和观察者模式

数据驱动

  • 数据响应式、双向绑定、数据驱动
  • 数据响应式
  • 数据模型仅仅是普通对象的 JavaScript,而我们修改数据时,视图会进行更新,避免了繁琐的 DOM 操作,提高开发效率
  • 双向绑定
  • 数据改变,视图改变,数据也随之改变
  • 我们可以使用 v-model 在表单元素上创建双向数据绑定

数据驱动是 Vue 最独特的特性之一

  • 开发过程中仅需要关注数据本身,不需要关系数据时如何渲染到视图

2、数据响应式的核心原理 Vue2

let data = {
    
  msg: "大白菜",
};
// 模拟Vue的实例
let vm = {};

// 数据劫持, 当访问或者设置vm中成员的时候,做一些干预操作
Object.defineProperty(vm, "msg", {
    
  // 可枚举
  enumerable: true,
  // 可配置 (可以使用delete杉树,也可通过defineProperty重新定义)
  configurable: true,
  get() {
    
    return data.msg;
  },
  set(newValue) {
    
    if (newValue === data.msg) {
    
      return;
    }
    data.msg = newValue;
    // 数据更改,更新DOM的值
    document.querySelector("#app").textContent = data.msg;
  },
});

// 测试
vm.msg = "Hello word";
console.log(vm.msg);

// 多个属性
let vm = {};
proxyData(data);

function proxyData(data) {
    
  Object.keys(data).forEach((key) => {
    
    Object.defineProperty(vm, key, {
    
      enumerable: true,
      configurable: true,
      get() {
    
        console.log("set:", key, data[key]);
        return data[key];
      },
      set(newValue) {
    
        if (newValue === data[key]) {
    
          return;
        }
        data[key] = newValue;
        document.querySelector("#app").textContent = data[key];
      },
    });
  });
}
// vm.msg = '大白菜'
// set: msg 大白菜

3、Vue 响应式原理 Vue3

  • MDN Proxy
  • 直接监听对象, 而非属性
  • ES6 中新增, IE 不支持,性能由浏览器优化
let data = {
    
  msg: "hello",
};

let vm = new Proxy(data, {
    
  get(target, key) {
    
    return target[key];
  },
  // 设置vm的成员会执行
  set(target, key, newValue) {
    
    console.log("set", key, newValue);
    if (target[key] === newValue) {
    
      return;
    }
    target[key] = newValue;
    document.querySelector("#app").textContent = target[key];
  },
});
vm.msg = "大白菜";
console.log(vm.msg);

4、发布订阅模式

  • 发布/订阅模式
  • 订阅者
  • 发布者
  • 信号中心 我们假定,存在一个“信号中心”,某个任务执行完成,就向信号中心“发布” (publish)一个信号,其他任务可以向信号中心“订阅” (subscribe)这个信号,从而知道什么时候自己可以开始执行,这就叫做“发布/定于模式” (publish-subscribe pattern)
let vm = new Vue();
// 注册事件(订阅消息)
vm.$on("dataChange", () => {
    
  console.log("dataChange");
});

vm.$on("dataChange", () => {
    
  console.log("dataChange1");
});
// 触发事件(发布消息)

// 自定义事件
class EventEmitter {
    
  constructor() {
    
    this.subs = Object.create(null);
  }

  // 注册事件
  $on(eventType, handler) {
    
    this.subs[eventType] = this.subs[eventType] || [];
    this.subs[eventType].push(handler);
  }
  // 触发事件
  $emit(eventType) {
    
    if (this.subs[eventType]) {
    
      this.subs[eventType].forEach((handler) => {
    
        handler();
      });
    }
  }
}

// 测试一下
let em = new EventEmitter();
em.$on("click", () => {
    
  console.log("click1");
});
em.$on("click", function () {
    
  console.log("click2");
});

em.$emit("click");

5、观察者模式

  • 观察者(订阅者) -- Watcher
  • upload(): 当事件发生时,
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值