Object.defineProperty,定义响应式的伪代码:
function defineProperty(target,key,value){
const dep = new Dep()
Object.defineProperty(target,key,{
get(){
if (Dep.target){
//依赖收集
dep.depend()
}
return value
},
set(newVal){
value=newVal
...
//通知更新
//dep.notify()
}
})
}
缺点:
- 无法检测到对象属性的新增或删除
由于js的动态性,可以为对象追加新的属性或者删除其中某个属性,这点对经过Object.defineProperty方法建立的响应式对象来说,只能追踪对象已有数据是否被修改,无法追踪新增属性和删除属性,这就需要额外的代码处理。 - 数组变化监听
vue2.x是通过代理数组原型,包装了一层数组的变异方法:'pop','shift','unshift','sort','reverse','splice', 'push' - get set 拦截器不能直接操作target对象
Proxy对象
var proxy = new Proxy(obj, handler)
obj是要代理的对象,handler是定制拦截操作,返回一个代理对象
特点:
Proxy代理是针对整个对象,不是针对对象属性做拦截
劣势:
- 性能比promise还差
- 兼容性不太乐观 ,无法完全polyfill
当然,Proxy也不是没有坑,尤其要注意代理对象方法的this指向问题;