proxy

1,395 阅读1分钟

前身-通过Object.defineProperty来实现拦截

  • 缺点:
    • 1.属性不存在无法监视到;
    • 2.性能很低,1,上来全部遍历都重新定义属性,2.对象嵌套很深,递归吃内存
let obj = {
    name: 'jaasdsa',
    age: { a: 100 }
}
function observer(obj) {
    if (typeof obj !== 'object') return;
    for (let key in obj) {
        let value = Reflect.get(obj, key);
        Object.defineProperty(obj, key, {
            enumerable: true,
            configurable: true,
            get() {
                if (typeof value === 'object') {
                    observer(value);
                }
                return value;
            },
            set(newValue) {
                update();
                value = newValue;
            }
        })
    }
}

function update() {
    console.log("视图更新");
}

// observer(obj);
// obj.name = 'jaa1';
// console.log(obj.name);

// obj.age.a = 12;
// console.log(obj.age.a);

Proxy

  • 优点:
    • 不存在属性也能监视到
    • 用到在定义属性,不用不定义
let o = {
    name: 'jaasdsa',
    age: { a: 100 }
}
let handler = {
    get(target, key) {
        let value = Reflect.get(target, key);
        if (typeof value === 'object') {
            return new Proxy(value, handler);
        }
        return value;
    },
    set(target, key, newVal) {
        update();
        return Reflect.set(target, key, newVal);
    }
}
let o1 = new Proxy(o, handler);

// o1.name = 'jaa1';
// console.log(o1.name);

// 嵌套属性也能代理到
o1.age.a = 123;
console.log(o1.age.a);
// 新增属性也能代理到
o1.sex = '1';
console.log(o1.sex);