为什么重置原型不会从对象中删除属性?

mró*_*ówa 9 javascript inheritance prototype

我试图了解javascript原型和可能的继承,但我肯定错过了一些东西.让我们从简单的构造函数(函数Counter())开始,添加对象的简单属性和实例化:

function Counter() { this.a = "first"; };
Counter.prototype.b = "second";
var counter = new Counter();
Run Code Online (Sandbox Code Playgroud)

此时,counter.a返回"first",counter.b返回"second" counter.c,当然undefined这是可以理解的.让我们为构造函数的原型添加另一个属性:

Counter.prototype.c = "third";  
Run Code Online (Sandbox Code Playgroud)

现在,counter.c将返回"第三".但是......我们已经改变了主意,让我们摆脱这些属性:

Counter.prototype = {};
Run Code Online (Sandbox Code Playgroud)

使用简单的逻辑,在覆盖counter原型的prototype属性时,我们会失去counter我们之前添加到Counter.prototype 的属性.但事实并非如此 - counter.c返回"第三".我迷失在这里.所以...让我们尝试覆盖价值:

Counter.prototype.c = "fourth hohoho";
Run Code Online (Sandbox Code Playgroud)

没有任何变化,counter.c仍然返回"第三".

为什么删除属性没有成功?我错过了什么?

Aln*_*tak 11

创建对象时,会将原型对象的引用添加到原型中.

您可以扩充该原型对象,并且由于实例共享引用,这些更改将反映在任何现有实例中.

但是,如果覆盖原型对象,则先前创建的实例仍保留对原始原型对象的引用.

它与此代码的情况相同:

var a = {};
var b = a;

a.foo = 'bar';    // augment 'a'
b.foo === 'bar';  // true

a = {};           // overwrite 'a'
b.foo === 'bar';  // still true
Run Code Online (Sandbox Code Playgroud)


bfa*_*tto 8

您可以动态地添加/删除原型对象中的属性,但不能替换已创建的实例的原型对象.在您的示例中,在替换构造函数的prototype属性之后创建的实例将获得新的原型,但之前创建的实例将保留对前一个对象的引用.

如果要从原型中清除某些属性,请使用delete运算符将其从原始对象中删除:

delete Counter.prototype.c;
Run Code Online (Sandbox Code Playgroud)