定义一个Javascript原型
以下两个Javascript原型之间的function差异是什么?select其中一个有什么好处?
选项1:
Person.prototype.sayName = function(name) { alert(name); }
选项2:
Person.prototype = { sayName: function(name) { alert(name); } }
我是否正确地认为选项2会导致某些隐含地绑定到原型的函数?
我是否正确地认为选项2会导致某些隐含地绑定到原型的函数?
对,就是这样。 虽然唯一的隐式绑定属性是你很less需要的constructor
属性。
有什么function差异?
选项1只是扩展了现有的原型。 如果已经有Person
实例inheritance自原型对象,那么他们也可以使用sayName
方法。 使用选项2,新的原型将仅用于覆盖后实例化的对象。
select一个在另一个上有什么好处吗?
这些应该是现在自我解释。 选项1(扩展)被认为是更清洁的,如果你修改外部/未知/本地原型,这是必须的。 尽量避免选项2。
如果您仍然更喜欢对象字面语法,则应考虑使用Object.assign
来扩展现有的原型:
Object.assign(Person.prototype, { sayName: function(name) { alert(name); } });
您可能需要为ES6之前的环境填充Object.assign
。 或者, $.extend
或_.extend
也可以。 当然,你最喜欢的库也有一个辅助函数。
第二个将用对象覆盖person.prototype。
方法一:
Object.toString=function(){ return "Object to string"; } var Person = function(){ }; Person.toString=function(){ return "Person to string"; } Person.prototype.sayName=function(){} console.log(Person.prototype.constructor.toString());// "Person to string"
方法二:
Object.toString=function(){ return "Object to string"; } var Person = function(){ }; Person.toString=function(){ return "Person to string"; } Person.prototype = { sayName:function(){} } console.log(Person.prototype.constructor.toString());// "Object to string"
首先是一两个额外的function,但是定义一个全新的具有多种function的原型将是非常重复的。 另一方面,如果你使用后者,则会破坏原型的所有定义。
在实践中,我已经使用第一个在Array和Math等中定义附加函数,有点像Objective-C中的类别。 后者我用作“类定义”。
任何现有的构造函数实例都将继续指向旧的原型对象。 任何新创build的实例都将指向新的原型对象。
选项1优于选项2的优点在于,您不必重新build立构造函数属性,就可以保存一个对我来说很重要的缩进级别。
为了节省重复,我只是把属性赋值给一个局部variables:
var method = Person.prototype; method.getAge = function() { return this.age; }; method.getName = function() { return this.name; };
也常见的select是fn
(jQuery)和p
甚至比method
更短。
简单的说就是Person.prototype.sayName
的区别在于你只需要在prototype
添加一个函数。 只是增加新的function。
在第二个Person.prototype = {}
这里,你正在创build一个新的整体对象,并将其分配给prototype
。 所以你创build一个新对象或用一个新对象覆盖prototype
。
第一种方法可以根据需要添加许多function。 您可以按时添加它们,所以当您的程序很简单并且您的应用程序对象没有共享太多的function或对象时,我认为它很好。
如果您的应用程序对象共享一些对象 (或者在Math functions
中用@isaach表示的一组Math functions
),那么第二种方法是很好的。