Object.defineProperty 和 Proxy
Object.defineProperty
弊端: 1. 对对象的添加和删除操作,无法劫持到,vue2新增 $set $delete 2. 对数组的api无法劫持到 vue2重新数组api 3. 存在深层嵌套关系,无脑递归
js
let person = { name: 'zs', age: 18, code: {name: 'qd'} }
function dPropery(obj, key, value) {
observer(value)
Object.defineProperty(obj, key, {
get: function() {
console.log('get', key)
return value
},
set: function(newValue) {
if (newVlue == value) return
observer(newValue)
console.log('set', key)
value = newValue
}
})
}
function observer(obj) {
if (typeof obj != 'object' || obj == null) {
return
}
for (let key in obj) {
dProperty(obj, key, obj[key])
}
}
Proxy
总结: 1. Proxy 直接可以劫持整个对象,并返回一个新对象,我们可以置操作新的对象达到响应式目的。 2. Proxy 可以直接监听数组变化。 3. Proxy 有多达13种拦截方法。 4. Proxy 通过懒加载,解决递归照成性能问题。 5. 不兼容IE
js
function reactive(obj) {
// Proxy 有13种监听方法 相对应Reflect也有13种映射关系
return new Proxy(obj, {
get(target, key) {
let res = Reflect.get(target, key)
return isObj(res) ? reactive(res) : res
},
set(target, key, value) {
return Reflect.set(target, key, value)
},
deleteProperty(target, key) {
return Reflect.deleteProperty(target, key, value)
}
})
}
funciton isObj(obj) {
if (typeof obj != 'obj' || obj == null) {
return false
}
return true
}
let person = reactive({ name: 'zs', age: 18, code: {name: 'qd'} })