我正在寻找对我怀疑的最好澄清。我有一个函数,从函数我调用一个方法,它工作正常。
示例:
function Car(){
this.name = 'car';
}
function Ferari(){}
Ferari.prototype = new Car;
Ferari.prototype.value = 122;
var fa = new Ferari;
console.log(fa.constructor, fa.name);
从控制台的输出我得到我的构造函数是'汽车'。我按如下方式更改了构造函数:
Ferari.prototype.constructor = Ferari;
现在构造函数控制台中的输出是'Ferari' - 没关系。
任何一个人都详细说明了上述问题?
答案 0 :(得分:1)
问题:
数目:
[A1]在某些情况下,有必要找出实例的真实构造函数,尤其是继承级别很深。例如https://github.com/chennanfei/ThinkMVC/blob/master/thinkmvc.js#L737。总之,要知道实例的确切构造对某些情况有帮助。
[A2]正如约翰所指出的那样,
Ferari.prototype = Object.create(Ferari.prototype);
Ferari.prototype.constructor = Ferari;
[A3]除非你明显使用它,否则我认为你不会遇到问题。
[A4]您的代码表示一般方式。我认为以下方式也有效。
var Cart = function() {...}
在评论中回答Johan的问题,我在这里补充了更多。 (文字的大小在评论中有限。) 这是一个有点复杂的案例。假设'class'Base提供了一个方法'setProtoValue',它允许实例设置/更新其原型的属性。类A和B继承自Base。当A的实例调用方法'setValue'时,我们当然不希望影响所有B的实例。所以我们需要知道A的确切构造函数。在下面的例子中,如果我们不重置A.prototype.constructor,包括B在内的所有Base实例都会受到影响,这是意料之外的。
var Base = function() {};
Base.prototype.setProtoValue = function(key, value) {
this.constructor.prototype[key] = value;
};
var A = function() {};
A.prototype = Object.create(Base.prototype);
A.prototype.constructor = A;
var B = function() {};
B.prototype = Object.create(Base.prototype);
B.prototype.constructor = B;
答案 1 :(得分:0)
好吧,正如您所看到的,如果您没有将构造函数声明为Ferrari
,那么将使用超类构造函数(以便Car
)。除非那是你想要的,否则请继续重新构建构造函数。
参见示例:
function Car(){
console.log('car');
}
function Ferari(){
console.log('ferrari');
}
Ferari.prototype = new Car;
//Ferari.prototype.constructor = Ferari;
var fa = new Ferari();
console.log(fa.constructor);
评论法拉利的重新声明,看看差异。
答案 2 :(得分:0)
如果执行Ferari.prototype = new Car;
,则无论是否创建Car
实例,都将调用Ferari
构造函数。
考虑到这一点,我建议进行以下更改:
function Car(){
console.log('car');
}
function Ferari(){
Car.apply(this, arguments); // Call the base class constructor manually
console.log('ferrari');
}
Ferari.prototype = Object.create(Ferari.prototype);
Ferari.prototype.constructor = Ferari;
var fa = new Ferari();