gpt4 book ai didi

javascript - 为什么在 JS 中你不能在原型(prototype)上设置非函数

转载 作者:行者123 更新时间:2023-11-30 07:58:30 25 4
gpt4 key购买 nike

我不确定如何表达标题,但这是一个让我大跌眼镜的例子

myLib.prototype._handlers = {};
myLib.prototype.destroy = function () {
this._handlers = {};
}

我正在编写测试,幸运的是它发现了这个问题。该 destroy 方法实际上不起作用。

为什么会这样?我认为原型(prototype)上的属性是为每个 new myLib 实例创建的新属性,但是通过编写这些测试 all new myLib 实例具有这些处理程序。

最佳答案

您可以在原型(prototype)上设置非函数。问题是原型(prototype)上的属性在对象的所有实例之间共享。这通常不是您想要的数据属性,但它是您想要的函数属性。

因此,您通常会在对象的构造函数中初始化数据属性,并使它们“拥有”属性,这些属性对于每个实例都是唯一的,这通常是您想要的。


I thought that properties on the prototype are created new for each new myLib instance, but from writing these tests all new myLib instances have these handlers.

原型(prototype)是一个用作属性查找机制的对象。当您引用 var x = obj.prop 时,Javascript 首先查看 obj 对象本身以查看是否存在名为 "prop" 的属性.如果存在,则将其视为“自己的”属性并获取其值。如果没有,则它会转到原型(prototype)对象以查看它是否具有名为 “prop” 的“自己的”属性。如果是,则返回该值。如果它没有那个命名的属性,那么它会检查原型(prototype)对象是否有它自己的原型(prototype),如果有,它会检查那个,依此类推...

因此,原型(prototype)用作查找引用。没有复制或创建任何新内容。只有对可用于查找的原型(prototype)的“引用”。这就是原型(prototype)在所有实例之间共享的原因。出于多种原因,它是故意这样设计的。原因之一是它的存储效率。所有实例都共享一个原型(prototype)对象,因此不必在每个对象实例上都复制所有这些引用。

当您分配给一个属性时:

obj.someProp = "foo";

它只会影响“自己的”属性(property)。它不影响原型(prototype)。如果名为 “someProp” 的对象有一个“own”属性,那么它的值会被更新。如果没有,则在实际对象实例上创建一个新的“自己的”属性。如果原型(prototype)上有这个名称的属性,那么该值现在基本上是隐藏的,因为 Javascript 属性查找方案将首先找到“自己的”属性,并从那时起使用它(只要它存在)。


当您在 .destroy() 方法中分配属性时,了解以下内容可能也很重要,例如:

myLib.prototype._handlers = {};
myLib.prototype.destroy = function () {
this._handlers = {};
}

当您执行 obj.destroy() 方法时,这实际上根本不会触及 myLib.prototype._handlers 值。相反,this._handlers = {}; 在对象的实际实例上创建一个新属性,一个“自己的”属性。任何对 this._handlers 的引用都将首先找到“自己的”属性,这就是从那时起将使用的属性,因此它可能“看起来”像它更改了原型(prototype)值,但新的“自己的”属性从那时起只是屏蔽了原型(prototype)值。

关于javascript - 为什么在 JS 中你不能在原型(prototype)上设置非函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34232195/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com