目录
定义与概念
JavaScript中的Proxy与Reflect是ES6中引入的新特性,它们可以帮助我们更高效地控制对象。
代理(Proxy)是一种设计模式,它允许我们在访问对象的同时,添加一些额外的操作。代理对象与被代理对象实现相同的接口,代理对象会接受并处理所有对被代理对象的访问请求。
代理是对象通过一个代理对象来控制对原对象的读取、设置、调用及其他操作,并对这些操作进行预处理或附加操作,主要用于拦截对象
反射(Reflection)是指程序可以在运行时获取、操作、修改它本身的状态或行为。反射是一种动态获取类型信息和操作类型的能力,可以在运行时动态调用类中的方法或属性。
反射可以使我们知晓(获取)对象详情,操控对象的成员(属性),在调用对象的方法时加入额外的逻辑,主要用于操作对象
在Java中,反射与代理可以通过reflect以及其中的Proxy类与InvocationHandler接口实现代理,通过reflect实现反射;而在C++中则是用继承和虚函数实现代理模式,使用模板和元编程修改检查结构达到反射。代理和反射通常都是编译时的概念,在编译阶段就已经确定了代理和反射的具体实现方式
而JS则是在运行时动态地创建代理和使用反射,并且提供了类似的概念和实现:全局的Proxy与Reflect对象
属性及函数
Proxy
使用new Proxy实例化时需要传入以下两个参数
- target:被代理的目标对象。
- handler:定义代理行为的对象。
handler参数中有一些钩子函数,在代理对象发生变化时会触发:
- get:在读取代理对象的属性时
- set:在对代理对象的属性进行赋值时
- has:在使用 in 运算符检查代理对象是否具有某个属性时
- deleteProperty:在删除代理对象的属性时
- apply:当前代理对象为函数,在调用代理对象时
- construct:在使用 new 运算符创建代理对象的实例时
- getOwnPropertyDescriptor:在获取代理对象的属性描述符时
- defineProperty:在定义代理对象的属性时
- getPrototypeOf:在获取代理对象的原型时
- setPrototypeOf:在设置代理对象的原型时
- isExtensible:在检查代理对象是否可扩展时
- preventExtensions:在防止代理对象的扩展时
- ownKeys:在返回代理对象的所有键时
Reflect
Reflect对象中的函数与上述handler中的钩子函数是一一对应的
- get:用于读取一个对象的属性值
- set:用于设置一个对象的属性值
- has:用于判断一个对象是否有某个属性
- deleteProperty:用于删除一个对象的属性
- apply:当前代理对象为函数,用于调用当前对象的方法
- construct:用于通过构造函数创建一个新的对象实例
- getOwnPropertyDescriptor:用于读