简体   繁体   English

为什么原型中定义的方法会显示在对象本身中?

[英]Why methods, defined in prototype, are shown in object itself?

Standard example for prototype inheritance learners: 原型继承学习者的标准示例:

function Animal(name) {
    this.name = name;
    this.speed = 0;
}

Animal.prototype.stop = function() {
    this.speed = 0;
};

Animal.prototype.run = function(speed) {
    this.speed += speed;
};

function Rabbit(name) {
    this.name = name;
    this.speed = 0;
}

Rabbit.prototype = Object.create(Animal.prototype);
Rabbit.prototype.constructor = Rabbit;

Rabbit.prototype.jump = function() {
    this.speed++;
};

var rabbit = new Rabbit('Bunny');

Looking at Google Chrome debugger, I can see the following picture: 查看Google Chrome调试器,可以看到以下图片: 原型JS继承

What confuses me: 令我困惑的是:

  1. Prototype of Rabbit is set to Animal . Rabbit原型设置为Animal
  2. jump() method is defined on Rabbit 's prototype - not on a Rabbit itself. jump()方法是在Rabbit的原型上定义的,而不是在Rabbit本身上定义的。
  3. Google Chrome shows jump() as part of Rabbit . 谷歌浏览器显示jump()作为Rabbit一部分。

It seems reasonable, because I don't want jump() to become part of Animal , but non-logical, because I define jump() on instance of Animal . 这似乎是合理的,因为我不希望jump()成为Animal一部分,而是不合逻辑的,因为我在Animal实例上定义了jump() Is there some special treatment for object in prototype property, like "set the object, defined in prototype as __proto__ , but move all additional methods definition into child objects"? prototype属性中的对象是否有某些特殊处理,例如“设置原型中定义为__proto__的对象,但将所有其他方法定义移到子对象中”? Or I get it wrong? 还是我弄错了?

To answer your questions: 要回答您的问题:

1) Prototype of Rabbit is set to Animal: 1)兔子的原型设置为动物:
You indicate this with the following code: 您可以使用以下代码进行指示:

Rabbit.prototype = Object.create(Animal.prototype);

Object.create() creates a new object with the prototype as the first argument. Object.create()创建一个以原型为第一个参数的新对象。
It's used to create the prototypes chain between Animal and Rabbit. 它用于创建Animal和Rabbit之间的原型链。

2) jump() method is defined on Rabbit's prototype - not on a Rabbit itself. 2)jump()方法是在Rabbit的原型上定义的,而不是在Rabbit本身上定义的。

It happens because you added this method exactly to the prototype, but not on the Rabbit instance. 发生这种情况是因为您已将此方法完全添加到了原型中,但没有Rabbit实例上添加。

Rabbit.prototype.jump = function() {
    this.speed++;
};

3) Google Chrome shows jump() as part of Rabbit. 3)Google Chrome显示出jump()作为Rabbit的一部分。
Yes, the jump() method is a part of the Rabbit: inherited from Rabbit.prototype. 是的, jump()方法是Rabbit的一部分:从Rabbit.prototype继承。

4) It seems reasonable, because I don't want jump() to become part of Animal, but non-logical, because I define jump() on instance of Animal 4)这似乎是合理的,因为我不希望jump()成为Animal的一部分,但是是非逻辑的,因为我在Animal实例上定义了jump()
You define jump() on a instance of Animal (a new instance, because Object.create() was used, but still keeping the Animal prototype), which becomes the prototype of Rabbit. 您可以在Animal实例(因为使用了Object.create(),但仍保留Animal原型)的新实例上定义jump() ,因此成为Rabbit的原型。

5)"set the object, defined in prototype as proto , but move all additional methods definition into child objects" 5)“将原型中定义的对象设置为proto ,但将所有其他方法定义移到子对象中”
It happens automatically on runtime, when an instance inherits properties and methods from the prototype object. 当实例从原型对象继承属性和方法时,它将在运行时自动发生。

One thing that may be confusing is why Google console shows: __proto__: Rabbit and __proto__: Animal . 可能令人困惑的一件事是Google控制台为何显示: __proto__: Rabbit__proto__: Animal Actually it displays the constructor function name, which is linked with the prototype objects. 实际上,它显示了构造函数名称,该名称与原型对象链接在一起。

You're only using the instance of Rabbit to get the prototype - but Animal has a reference to that same prototype - in essence, Rabbit extends Animal (or vice versa). 您仅使用Rabbit实例获取原型-但Animal引用了同一原型-本质上,Rabbit扩展了Animal(反之亦然)。 So if you change the Rabbit's prototype, you change the Animal's prototype too. 因此,如果您更改Rabbit的原型,也将更改Animal的原型。

You could define jump in the rabbit itself, not the prototype. 您可以在兔子本身而不是原型中定义跳转。 Alternatively, you could set the Rabbit's prototype to a new Animal object and modify that. 另外,您可以将Rabbit的原型设置为新的Animal对象,然后对其进行修改。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 为什么在对象本身(例如Function.name)上定义Function属性,而在Function.prototype上定义方法? - Why do Function properties are defined on the object itself (e.g. Function.name), but methods - on Function.prototype? 为什么JavaScript中的对象不能成为它自己的原型? - Why can't an object in JavaScript be a prototype of itself? 模拟“类”时,为什么要在.prototype属性中而不是在构造函数本身中设置方法? - When emulating a 'class', why set the methods in the .prototype property and not in the constructor itself? 为什么函数中创建的属性和方法没有显示在该函数原型的构造函数属性中? - Why are the properties and methods created in a function not shown in the constructor property of the prototype of that function? 为什么在原型中定义了实例方法,但在构造函数中定义了实例字段? - Why are instance methods defined in the prototype but instance fields are defined in the constructor? 为什么只显示用class.prototype定义的方法? - why does for … in only show methods defined with class.prototype? 为什么没有将ES5 Object方法添加到Object.prototype? - Why were ES5 Object methods not added to Object.prototype? 为什么在执行 Object.create(null) 之后将其原型设置为 Object.prototype 将不允许执行 Object.prototype 中的方法 - Why doing Object.create(null) and later setting its prototype to Object.prototype will not allow to execute methods in Object.prototype 为什么Object.getOwnPropertyNames()也会在原型上提供方法? - Why Object.getOwnPropertyNames() gives the methods on the prototype too? 为什么对象原型方法会覆盖JavaScript中的String和Number原型方法? - Why would an Object prototype method override String and Number prototype methods in JavaScript?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM