2

我不明白以下行为:

var Foo = function () {};
var Bar = function () {};
Foo.prototype = Bar;
var foo = new Foo();
console.log(foo.prototype === Bar.prototype); // true, but why?

我在规范中找不到关于prototype使用构造函数创建的对象的属性默认值的任何内容。(我确实找到了规范的这一部分,其中提到,对于函数,prototype属性默认为new Object(),但没有提到使用构造函数创建的对象。)

所以,我的问题实际上是双重的:

prototype使用构造函数创建的对象的属性的默认值是多少?(似乎它是构造函数prototypeprototype属性;例如Foo.prototype.prototype

它在规范中的哪里解释了这种行为?

4

2 回答 2

2

prototype使用构造函数创建的对象的属性的默认值是多少?

undefined,除非你正在构建的是一个函数。该prototype属性属于函数。如果实例对象在其 prortype 链中没有函数对象(即instanceObj instanceof Functionis false),则该实例通常不会有prototype属性。

函数具有prototype属性的原因是因为任何函数有一天都可能用作构造函数。构造函数的prototype属性决定了[[Prototype]]其构造实例的内部属性。

(似乎它是构造函数prototypeprototype属性;例如Foo.prototype.prototype

您只能看到行为,因为您已分配Foo.prototype 给 functionBar。因此,当您尝试获取foo.prototype时,解释器会查找foo的原型链并找到prototype函数的属性Bar

特别是,foo.prototype === Bar.prototype因为:

  1. 要得到foo.prototype,我们首先要尝试prototype下车foo
  2. foo没有prototype财产。
  3. 查找原型链:foo's[[Prototype]]设置为何Foo.prototypefoo构造。(记住,Foo.prototype是函数Bar。)
  4. prototype在上寻找Bar
  5. 成功!Bar.prototype被定义为。将其用于foo.prototype.
  6. 不出所料,Bar.prototype等于Bar.prototype

它在规范中的哪里解释了这种行为?

  • 15.3.5.2解释了该prototype属性被用作[[Prototype]]其构造对象的内部属性。

  • 13.2.2(步骤 5 - 7)详细说明了上面 15.3.5.2 中描述的确切程序。

  • 8.6.2描述了一般的基于原型的继承(即,如果一个对象没有属性,查看它的属性[[Prototype]],等等)

于 2013-07-24T19:17:41.793 回答
2

构造对象的原型是构造函数的.prototype属性所引用的对象。

所以因为foo.__proto__ === Bar,那么显然foo.__proto__.prototype = Bar.prototype

foo对象没有属性,因为对象的原型是具有原型属性的函数对象.prototype,所以查找并找到它,这是您错过的。foo.__proto__

于 2013-07-24T19:11:23.007 回答