我想知道这个
之间有什么区别 MyClass = function() {};
MyClass.prototype.Foo = function();
和这个
MyClass = {};
MyClass.prototype.constructor = function() {};
MyClass.prototype.Foo = function();
在JavaScript中声明原型的构造函数时。
使用prototype.constructor
优于常规函数有什么好处?
答案 0 :(得分:6)
查看以下图片,取自following answer:
当您创建新函数时,JavaScript也会自动创建一个新对象(原型):
prototype
属性设置为原型对象。constructor
属性设置为构造函数。因此当你这样做时:
function Foo() {}
JavaScript实际上是这样做的:
function Foo() {}
Foo.prototype = { constructor: Foo };
为什么JavaScript会这样做?考虑一下创建Foo
的实例时会发生什么:
var foo = new Foo;
使用Foo
关键字创建new
的实例时,JavaScript实际上会创建Foo.prototype
而非Foo
的实例。这意味着foo
继承了Foo.prototype
而非Foo
的属性。为了明确这一点:
function Foo() {}
Foo.bar = true;
Foo.prototype.baz = true;
var foo = new Foo;
alert(foo.bar); // undefined
alert(foo.baz); // true

现在,在原型上具有constructor
属性的优点是,当您创建Foo
的实例时,该实例将从原型继承constructor
属性。因此,您可以使用它来找出对象的类型:
function Foo() {}
function Bar() {}
function test(obj) {
switch (obj.constructor) {
case Foo: alert("It's a Foo."); break;
case Bar: alert("It's a Bar."); break;
default: alert("It's something else.");
}
}
test(new Foo);
test(new Bar);
test(new Object);

除此之外,原型的constructor
属性并没有什么特别之处。它只是一个普通的财产。用Tyler Durden的话来说:https://www.youtube.com/watch?v=4X2AvfSTi6Q
由于它是一个普通的属性,你可以决定根本没有构造函数属性:
function Foo() {}
Foo.prototype = {}; // no constructor property
你可以决定让它指向其他一些功能:
function Foo() {}
function Bar() {}
Foo.prototype.constructor = Bar;
您可以决定使其指向功能以外的其他内容:
function Foo() {}
Foo.prototype.constructor = "I am not a function.";
然而,重点是它只是另一个原型属性。实际上,我们可以利用它来创建更清晰的代码。例如,这就是我们通常创建"类"在JavaScript中。
function MyClass(a, b) {
this.a = a;
this.b = b;
}
MyClass.prototype.sum = function () {
return this.a + this.b;
};
MyClass.prototype.diff = function () {
return this.a - this.b;
};
它不是很干净。但请注意,所有三个函数MyClass
,sum
和diff
都是原型函数:constructor
,sum
和diff
。原型只是一个对象,JavaScript中的对象文字提供了一种很好的封装形式。我们可以利用这个来编写更清晰的代码:
function defclass(prototype) {
var constructor = prototype.constructor;
constructor.prototype = prototype;
return constructor;
}
var MyClass = defclass({
constructor: function (a, b) {
this.a = a;
this.b = b;
},
sum: function () {
return this.a + this.b;
},
diff: function () {
return this.a - this.b;
}
});
那更清洁了。此外,它向我们展示了constructor
属性只是一个普通的原型属性。希望能回答你的问题。
答案 1 :(得分:0)
MyClass.prototype.Foo = function(); 此代码为类MyClass添加一个静态函数,这意味着它的实例可以通过点运算符来识别Foo函数。 当我们做新的MyClass时,首先,我们创建一个像{}这样的空白对象,然后我们调用对象上的构造函数(MyClass.prototype.constructor.apply(obj,args)),最后,我们设置了原型MyClass到对象的原型并返回对象。 因此,当您编写" MyClass.prototype.constructor = function(){}"时,上面的第二步将不执行任何操作。