请说一下你对响应式数据的理解?


1.1 如何实现响应式数据

数组和对象类型当值变化时如何劫持到。对象内部通过defineReactive方法,使用Object.defineProperty将属性进行劫持(只会劫持已经存在的属性),数组则是通过重写数组方法来实现。 多层对象是通过递归来实现劫持。Vue3则采用 proxy

1.2 vue2 处理缺陷

  • Vue2 的时候使用 defineProperty 来进行数据的劫持, 需要对属性进行重写添加gettersetter 性能差
  • 当新增属性和删除属性时无法监控变化。需要通过$set$delete实现
  • 数组不采用 defineProperty 来进行劫持 (浪费性能,对所有索引进行劫持会造成性能浪费)需要对数组单独进行处理。
  • 对于 ES6 中新产生的 Map、Set 这些数据结构不支持。

1.3 Vue2Vue3 实现对比

Vue2

function defineReactive(target,key,value){
    observer(value);
    Object.defineProperty(target,key,{ ¸v
        get(){
      		//依赖收集
            return value;

        },
        set(newValue){
            if (value !== newValue) {
                value = newValue;
                observer(newValue)
            }
        }
    })
}
function observer(data) {
    if(typeof data !== 'object'){
        return data
    }
  //	依赖更新
    for(let key in data){
        defineReactive(data,key,data[key]);
    }
}

vue3

let handler = {
  get(target, key) {
    if (typeof target[key] === "object") {
      return new Proxy(target[key], handler)
    }
    return Reflect.get(target, key)
  },
  set(target, key, value) {
    let oldValue = target[key]
    if (oldValue !== value) {
      return Reflect.set(target, key, value)
    }
    return true
  },
}
let proxy = new Proxy(obj, handler)

总结:

Vue2 源码 ,Vue3 源码


文章作者: 高红翔
版权声明: 本博客所有文章除特別声明外,均采用 CC BY 4.0 许可协议。转载请注明来源 高红翔 !
  目录