将Object.create()的结果作为arg传递给Object.create()无法正常工作

时间:2015-05-15 09:53:04

标签: javascript

var Parent = Object.create(null);

Object.defineProperties(Parent, {
    __name: {
        value: 'tom'
    },
    __age: {
        value: 26
    },
})

var foo =  Object.create(Parent); // {} No Properties

为什么Object.create(Parent)无法从Parent

获取属性__name和__age

1 个答案:

答案 0 :(得分:2)

  

为什么Object.create(Parent)无法从Parent

获取属性__name和__age

确实,您只是通过Object.keys或类似的方式来寻找它们,它们只显示对象的拥有属性,而不是它继承的属性来自它的原型。

如果您使用in"__name" in foo),您会看到该属性存在,如果您访问它,您将从原型中获取值。

我们无法使用foo.hasOwnProperty(不是直接),因为Parent有一个null原型,而不是通常的Object.prototype。因此,foo不会继承Object.prototype中的常规内容。我们可以使用间接,但是:Object.prototype.hasOwnProperty.call(foo, "__name")。那就是false,因为它不是自己的财产,而是继承的。

以下是一个示例,其中包含各种检测属性及其结果的方法(根据我们查看继承属性的方式而有所不同):

var Parent = Object.create(null);

Object.defineProperties(Parent, {
    __name: {
        value: 'tom'
    },
    __age: {
        value: 26
    },
})

var foo = Object.create(Parent);
snippet.log(foo.__name);                                // tom
snippet.log(foo.__age);                                 // 26

snippet.log("__name" in foo);                           // true, it's there
snippet.log(Object.hasOwnProperty.call(foo, "__name")); // false, it's inherited
snippet.log(JSON.stringify(Object.keys(foo)));          // [] - object.keys only looks at "own" properties
<!-- Script provides the `snippet` object, see http://meta.stackexchange.com/a/242144/134069 -->
<script src="http://tjcrowder.github.io/simple-snippets-console/snippet.js"></script>

重新评论:

  

为什么在devtool中调试时没有[[proto]]属性引用foo中的Parent

我认为你的意思是__proto__,而不是[[proto]]。他们不是一回事。 __proto__访问者属性,如果存在,则访问对象的[[proto]]。 Chrome的devtools会显示__proto__是否存在。但是foo没有。为什么不?由于__proto__Object.prototype的一部分(请参阅§B.2.2.1 of the draft spec),而foo不会继承Object.prototype,因为它继承自Parent没有原型,因为它是通过Object.create(null)创建的。

通过foo我们可以看到Parent有一个原型,而且它是Object.getPrototypeOf

var Parent = Object.create(null);

Object.defineProperties(Parent, {
    __name: {
        value: 'tom'
    },
    __age: {
        value: 26
    },
})

var foo = Object.create(Parent);
snippet.log(foo.__proto__ === Parent);              // false, foo doesn't have __proto__
snippet.log(Object.getPrototypeOf(foo) === Parent); // true, Parent is foo's prototype
<!-- Script provides the `snippet` object, see http://meta.stackexchange.com/a/242144/134069 -->
<script src="http://tjcrowder.github.io/simple-snippets-console/snippet.js"></script>