qwe*_*ynl 16 javascript object
我们假设我有以下对象构造函数:
function Foo(bar) {
this.bar = bar;
}
Run Code Online (Sandbox Code Playgroud)
如果我在没有new关键字的全局范围内运行该函数,那么bar将在以下任何范围内设置Foo():
var foo = Foo(42);
console.log(bar); // 42
console.log(foo.bar); // ERROR
Run Code Online (Sandbox Code Playgroud)
所以我的想法是做这样的事情:
function Foo(bar) {
if(!(this instanceof Foo)) {
// return a Foo object
return new Foo(bar);
}
this.bar = bar;
}
Run Code Online (Sandbox Code Playgroud)
这样,如果我做的new Foo(42) 还是 Foo(42),它会始终返回一个Foo对象.
这是有史以来一个好主意?如果是的话,何时?何时(和为什么)避免这种技术是明智的?
虽然我没有任何反对这种风格的东西,但我个人并不只是为了保持一致.当然,我可以使我的所有构造函数都像这样,但看起来似乎要编写更多的代码.
如果我担心没有意外调用构造函数new,我宁愿使用JSHint来警告我.请参阅http://www.jshint.com/docs/options/#newcap.
当您希望在内部构造对象包装器时,这可能很有用.
一个鲜为人知的库在内部使用这种方法,jQuery.
他们不再使用这种instanceof方法了.每次调用jQuery时,它都会自动执行以下操作:
// Define a local copy of jQuery
jQuery = function( selector, context ) {
// Need init if jQuery is called (just allow error to be thrown if not included)
return new jQuery.fn.init( selector, context );
}
Run Code Online (Sandbox Code Playgroud)
它在内部所做的一切都引用了这个本地副本.在其工作的最后,它将其附加到全球范围
window.jQuery = window.$ = jQuery;
Run Code Online (Sandbox Code Playgroud)
所以每次你$()在内部使用时都会调用它new.它也假设您不使用new外部,但如果您不这样做,它真的不在乎.
编辑
//Foo entrance
function Foo(bar){
//construct a new Foo object to return
return new Foo.prototype.build(bar);
}
//constructor for returning new prototype
Foo.prototype.build = function(bar){
//initialize base settings
this.bar = bar;
//chain object
return this;
};
//this is the complex part
//tie the prototype of Foo.prototype.build.prototype to Foo.prototype
//so that is "seems" like Foo is the parent of the prototype assignments
//while allowing for the use of returning a new object in the Foo entrance
Foo.prototype.build.prototype = Foo.prototype;
//simple expansions at this point, nothing looks too different
//makes a function for a constructed Foo that logs hello
Foo.prototype.hello = function(){
console.log("Hello "+this.bar+" :)");
//returns this for chaining
return this;
};
//more extensions, this one changes this.bar's value
Foo.prototype.setBar = function(arg){
//accesses the current Foo instance's .bar property
this.bar = arg;
//returns this for chianing
return this;
};
//should be seeing a pattern
Foo.prototype.goodbye = function(){
console.log("Bye "+this.bar+" :(");
return this;
};
var foo = Foo(42);
//console.log(bar); // ERROR
console.log(foo.bar); // 42
foo.hello(); //Hello 42 :)
foo.hello().setBar(9001).goodbye(); //Hello 42 :) Bye 9001 :(
Foo(12).hello(); //Hello 12 :)
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
1142 次 |
| 最近记录: |