反射应用编程接口为对象提供运行时级别的元操作。这实际上与代理应用编程接口相反,允许调用与代理陷阱相同的元操作。Reflect
对象是静态对象。您不能创建它的实例。同样,它的所有方法都是静态的。你可能认为我们已经有了一些类似 JavaScript 的反射方法,但是最大的区别是Reflect
提供了更有意义的返回值。
考虑以下示例:
代码清单 208
let obj = {}, name = "matt",
desc = "here
we go";
try {
Object.defineProperty(obj, name, desc);
// worked.
}
catch (e) {
// error.
}
if (Reflect.defineProperty(obj, name, desc)) {
// worked
}
else {
// error.
}
在第一部分中,我们有一个 try/catch 块,我们使用的是Object.defineProperty
方法。在这个例子中,这个方法只返回传递给它的第一个参数。但是,看一下Reflect.defineProperty
方法,我们看到它返回了一个布尔值,这要有意义得多。
让我们考虑另一个例子:
代码清单 209
let obj = { a: 1 };
Object.defineProperty(obj,
"b", { value: 2 });
obj[Symbol("c")] =
3;
console.log(Reflect.ownKeys(obj));
// [ "a", "b", Symbol(c) ]
如您在本例中所见,Reflect.ownKeys
为我们提供了基于字符串和符号的键。
以下是Reflect
对象包含的所有方法:
Reflect.get(target, name, [receiver])
Reflect.set(target, name, value, [receiver])
Reflect.has(target, name)
Reflect.apply(target, receiver, args)
Reflect.construct(target, args)
Reflect.getOwnPropertyDescriptor(target, name)
Reflect.defineProperty(target, name, desc)
Reflect.getPrototypeOf(target)
Reflect.setPrototypeOf(target, newProto)
Reflect.deleteProperty(target, name)
Reflect.enumerate(target)
Reflect.preventExtensions(target)
Reflect.isExtensible(target)
Reflect.ownKeys(target)