16.md 1.9 KB
Newer Older
W
wizardforcel 已提交
1 2
# 十六、反射 API

W
wizardforcel 已提交
3 4 5 6 7 8
反射应用编程接口为对象提供运行时级别的元操作。这实际上与代理应用编程接口相反,允许调用与代理陷阱相同的元操作。`Reflect`对象是静态对象。您不能创建它的实例。同样,它的所有方法都是静态的。你可能认为我们已经有了一些类似 JavaScript 的反射方法,但是最大的区别是`Reflect`提供了更有意义的返回值。

考虑以下示例:

代码清单 208

W
wizardforcel 已提交
9
```js
W
wizardforcel 已提交
10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40
  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

W
wizardforcel 已提交
41
```js
W
wizardforcel 已提交
42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69
  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)`