JavaScript描述符:默认情况下,枚举/可配置/可写是不正确的?

时间:2017-01-17 21:19:33

标签: javascript descriptor

我在new ES5 features上阅读John Resig的一个博客,其中一个是Object描述符。在他的博客早期,约翰写道:

  

三个属性(可写,可枚举和可配置)都是   可选,默认为true。因此,你唯一的财产   需要提供的将是价值或获取和设定。

后来他提供了一个例子:

var obj = {};

Object.defineProperty( obj, "propertyname", {
    value: true,
    writable: false,
    enumerable: true,
    configurable: true
});

(function() {
    var name = "John";

    Object.defineProperty( obj, "name", {
        get: function(){ return name; },
        set: function(value){ name = value; }
    });
})();

但是,在检查name的属性描述符时,它不可配置或可枚举,因此我无法在for循环中访问它。

console.log(Object.getOwnPropertyDescriptor(obj, 'name'))
> Object {enumerable: false, configurable: false}

name不应该是可枚举的和可配置的吗?我在这里缺少什么?

2 个答案:

答案 0 :(得分:4)

the spec开始,默认情况下,数据属性是不可配置的,不可枚举且不可写。

  

如果属性的属性的初始值未明确   由本规范指定,使用Table 4中定义的默认值。

     

表4:默认属性值

┌──────────────────┬─────────────────┐
│  Attribute Name  │  Default Value  │
├──────────────────┼─────────────────┤
│ [[Value]]        │ undefined       │
│ [[Get]]          │ undefined       │
│ [[Set]]          │ undefined       │
│ [[Writable]]     │ false           │
│ [[Enumerable]]   │ false           │
│ [[Configurable]] │ false           │
└──────────────────┴─────────────────┘

但是,当您通过赋值创建数据属性时,CreateDataProperty将其定义为可配置,可枚举和可写。

  

newDesc 成为PropertyDescriptor {[[Value]]: V ,[[Writable]]:   true,[[Enumerable]]:true,[[Configurable]]:true}。

答案 1 :(得分:1)

描述符属性的默认值为false或undefined。

博客有错误。除非在描述符中明确定义,否则enumerable / configurable / writable将为falsevalue将为undefined。访问者描述符属性也将默认为undefined

这与MDN notes

同时发生
  

数据和访问者描述符都是对象。它们共享以下所需的密钥:

     

<强>配置

     

当且仅当此属性描述符的类型为true时才为true   如果财产可能被删除,可能会被更改   相应的对象。默认为false。

     

<强>枚举

     

当且仅当在枚举相应对象的属性期间显示此属性时才显示true。默认为false。

     

数据描述符还具有以下可选键:

     

     

与财产相关的价值。可以是任何有效的   JavaScript值(数字,对象,函数等)。默认为   未定义。

     

<强>可写

     

当且仅当与之关联的值时才为true   可以使用赋值运算符更改属性。默认为   假。

     

访问者描述符还具有以下可选键:

     

获取

     

用作属性的getter或undefined的函数   如果没有吸气剂。函数return将用作值   财产。默认为未定义。

     

设置

     

作为一个功能   属性的setter,如果没有setter,则为undefined。该   函数将仅接收分配给新值的参数   财产。默认为undefined。