是否有效而不是这样做
function Animal(name, numLegs) {
this.name = name;
this.numLegs = numLegs;
}
Animal.prototype.sayName = function() {
console.log("Hi my name is " + this.name);
};
function Penguin(name) {
this.name = name;
this.numLegs = 2;
}
Penguin.prototype = new Animal();
var penguin = new Penguin("Tux");
penguin.sayName();
那样做?
function Animal(name, numLegs) {
this.name = name;
this.numLegs = numLegs;
}
Animal.prototype.sayName = function() {
console.log("Hi my name is " + this.name);
};
function Penguin(name) {
return new Animal(name, 2);
}
Penguin.prototype = new Animal();
var penguin = new Penguin("Tux");
penguin.sayName();
我发现第二个版本更优雅,希望两个版本的结果相同,但第二个版本codeacademy告诉我
Oops, try again. Make sure to create a new Penguin instance called penguin!
而第一个被接受。
答案 0 :(得分:1)
我认为不同之处在于构造函数不会返回值。所以,如果你打电话
new Penguin('bla')
返回新对象的不是Penguin函数,而是返回新Object的 new 。因此,如果你让Penguin()返回一个新的Object,这将与new-keyword相冲突。
如果要调用父构造函数,可以按如下方式执行:
function Penguin(name) {
Animal.call(this, name, 2);
}
另外:当你将Animal的原型分配给它的子原型企鹅时,你可以在没有参数的情况下调用你的例子中的函数。有一种更简洁的方法:
Penguin.prototype = Object.create(Animal.prototype);
之后你丢失了Penguin的构造函数,所以你需要像这样重新分配它:
Penguin.prototype.constructor = Animal;
这里有详细解释: https://developer.mozilla.org/en-US/docs/Web/JavaScript/A_re-introduction_to_JavaScript
和 https://developer.mozilla.org/en-US/docs/Web/JavaScript/Introduction_to_Object-Oriented_JavaScript
答案 1 :(得分:1)
这不是调用父构造函数的正确方法:
function Penguin(name) {
return new Animal(name, 2);
}
正确的方法如下:
function Penguin(name) {
Animal.call(this, name, 2);
}
原因在于new
的工作方式:
ABC
的函数。new ABC
时,JavaScript会创建ABC.prototype
的实例,并将其绑定到函数this
内的ABC
,这就是为什么可以向{{1}添加属性的原因} {} this
。ABC
,除非您明确返回另一个对象。 Codecademy抱怨您的代码的原因是因为您返回的this
不 new Animal(name, 2)
instanceof
。
正如我之前所说,调用父构造函数的正确方法是使用Penguin
。在这种情况下,我们将父构造函数中的ParentConstructor.call(this, arg1, arg2, ...)
设置为与当前构造函数(由this
创建的实例)中的this
相同的值。
如果您想编写优雅的代码,请尝试使用以下尺寸:
new
使用function defclass(prototype) {
var constructor = prototype.constructor;
var instance = prototype.instance = function () {};
constructor.prototype = instance.prototype = prototype;
return constructor;
}
function extend(parent, keys) {
var supertype = keys.super = parent.prototype;
var prototype = new supertype.instance;
for (var key in keys) prototype[key] = keys[key];
return defclass(prototype);
}
和defclass
,您可以按如下方式重写代码:
extend
那有多酷?
答案 2 :(得分:0)
在第二个示例中,您不会返回Penguin的实例,而是返回Animal的实例。如果你想为penguin添加更多功能,你需要使用额外的功能来装饰Animal类。
function Penguin(name) {
var self = new Animal(name, 2);
self.penguinFunction = function (){
//do something here
}
return self;
}