JavaScript的原型链

时间:2017-03-10 14:29:49

标签: javascript

我在JavaScript中学习原型链并编写了一个演示,但我无法理解结果。

这是我的演示:

function A(){}
const c = new A();
A.prototype.sex = "girl";
A.prototype={
  name:"q",
  age:12
};
console.log(A.prototype.name);
console.log(c.name);
console.log(c.sex);

这是输出:

"q"
undefined
"girl"

为什么console.log(c.name)输出undefined

3 个答案:

答案 0 :(得分:3)

A是你的构造函数,这意味着当你初始化"时,你需要在新创建的对象上输入你需要的所有东西。它

在你的情况下,你什么都不做。 构造函数有一个prototype属性,该对象是您将由new A()创建的所有对象将继承自

如果您没有明确地将原型设置为构造函数,那么默认情况下您的原型是一个空对象。

所以在那一行:const c = new A(); c继承一个空对象 当你设置:

A.prototype.sex = "girl";

你正在空对象上创建一个属性,然后你分配给它" girl"

但是这个对象与之前相同(相同的参考)" new"。因此c仍有参考 但是当你这样做时:

A.prototype={
  name:"q",
  age:12
};

你改变A的原型,即改变A.prototype的引用,但你不再使用new了。所以没有实际拥有的对象

{
      name:"q",
      age:12
    }

作为原型。 c仍然将前一个对象(记住空的)对象作为原型。

但是如果你这样做:const d = new A()那么,d.name将会存在但d.sex赢了

像你一样改变原型(指定对A.prototype的另一个引用)只会影响A.prototype,而不会影响已经实现的对象'在那次做作之前。

答案 1 :(得分:1)

以下是根据JavaScript spec构建新对象的步骤。

正如您在步骤5和6中所看到的,构造对象的内部原型在构造期间被确定并捕获。

因此,该对象不会维护对“Wither .prototypeA在任何给定时间”的原型引用。它维护了A.prototype执行new A()时所具有的价值”的原型参考。这就是为什么你可以通过向它添加新属性来修改c的内部原型,而不是用新的原型替换A的原型。

如果您在更换原型后再次执行new A() ,那么当时创建的对象将具有该新原型。

  
      
  1. 让obj成为新创建的本机ECMAScript对象。
  2.   
  3. 按照8.12中的规定设置obj的所有内部方法。
  4.   
  5. 将obj的[[Class]]内部属性设置为“Object”。
  6.   
  7. 将obj的[[Extensible]]内部属性设置为true。
  8.   
  9. proto 成为使用参数“prototype”调用F的[[Get]]内部属性的值。
  10.   
  11. 如果Type( proto )是Object,请将obj的[[Prototype]]内部属性设置为 proto
  12.   
  13. 如果Type(proto)不是Object,则将obj的[[Prototype]]内部属性设置为标准内置Object原型对象,如15.2.4中所述。
  14.   
  15. 让结果成为调用F的[[Call]]内部属性的结果,提供obj作为此值,并将传递给[[Construct]]的参数列表作为args。
  16.   
  17. 如果Type(result)是Object,则返回结果。
  18.   
  19. 返回obj。
  20.   

答案 2 :(得分:0)

1)你创建一个空类

2)你添加一个静态属性(来自原型)性

3)你为你的班级分配了一个新的原型,但是c保留旧原型

所以'A'是最新的,但'c'仍然得到旧的原型,所以名称不存在,但在更改原型之前设置的性属性存在,所以你找到它。