我最近一直在研究一些JS库,这些库是由真正知道自己在做什么的人编写的,我一直在看到这种模式,但我找不到有关它的信息。我阅读了有关.call()方法的文档,但它对我来说并不真正有意义。我希望得到一个好的老经典的深入解释,所以用例子。
(function(undefined){
/*(insert entire library here)*/
}).call(this);这是关于什么的?为什么这是一个写库的好方法?
请注意,有时会省略undefined,尽管我不知道放在那里或不放有什么区别。我甚至不知道参数是从哪里来的,也不知道调用者是谁。
发布于 2013-09-24 07:05:34
让我们反汇编这段代码。
首先,有一个带有立即调用的匿名函数。它类似于这个:
(function () {/**/}).call();
(new Date()).getTime(); // timestamp since 1970 jan 1 in milliseconds我们不会将new Date()赋值给变量,而是立即使用它。
现在为什么要使用.call而不只是()
.call是所有Functions都有的方法。第一个参数是this将绑定到的参数,随后的参数将作为参数传递给函数。所以:
(function () {
console.log(this.foo); // bar
}).call({ "foo": "bar" });这与undefined协同工作(见下文)。
.call与.apply相同,只是有一点小小的不同。.apply只有两个参数,其中第二个参数是一个参数数组。这将是类似的:
(function () {}).call(this, "foo", "bar");
(function () {}).apply(this, [ "foo", "bar" ]);apply的一个常见用法是与神奇的变量arguments结合使用。
(function () {
console.log(Array.prototype.slice.call(arguments, 1)); // [ "bar" ]
})([ "foo", "bar" ]);Array.prototype.slice.call(arguments, 1)看起来可能很可怕,但实际上它只是arguments.slice(1),但arguments不是Array,所以它没有slice函数。我们借用Array的slice函数并使用.call将this设置为arguments。Array.prototype.slice(arguments, 1??)不正确。
为什么.call(this)中会有this?this总是指向你所处的上下文。如果你在一个类的实例中,它将指向该实例,如果你在全局作用域中,它将指向该实例。在浏览器环境中,它也是window。
为什么是undefined?因为我们做了一个没有第二个参数的.call(this),所以匿名函数的所有参数都是undefined。我真的不确定为什么需要在那里创建一个名为undefined的显式变量。也许这是对某些浏览器或某些lint工具的支持,这些浏览器或工具希望看到定义的undefined。
感谢@TedHopp。undefined是反复无常的。
var undefined = "foo";
console.log(undefined); // undefined
(function (undefined) {
console.log(undefined); // "foo"
})("foo");你可以很容易地拥有:
(function () {
/* code here */
}());这是完全有效的,工作起来也是一样的。使用您发布的表单可能会带来一些性能或线条上的好处。
https://stackoverflow.com/questions/18970112
复制相似问题