!function(){ }() vs (function(){ })()

30

在审查Twitter Bootstrap Javascript中的一些代码时,看起来它们像这样调用立即调用的匿名函数:

!function( $ ) {

     ...

}(window.jQuery || window.ender);

我以前通常是用这种方法来完成同样的事情:

(function($) {

    ...

})(window.jQuery || window.ender);

第一种方式似乎有点不正规,我不确定为什么要这样做而不是第二种方式?请注意,我知道它的工作原理,我想知道他们选择这种方式的原因。


10
这是一篇由撰写此文的人所写的博客文章 - icktoofay
可能是[(function(){})();]和[function(){}();]之间的不同,以及JavaScript中括号表示法是否有用于自调用函数?的重复问题。 - outis
3
我不相信这是一个重复问题;这个问题问的是为什么要用!function(){}()而不是(function(){})(),而不是比较(function(){})()function(){}()。在某些情况下,后者会导致语法错误,前两种都不会。 - icktoofay
谢谢@icktoofay,现在我已经阅读了它并仔细查看了它的编写方式...大部分都让我非常烦恼 ;) - jondavidjohn
1
可能是函数前的感叹号是做什么的?的重复问题。 - Matt Handy
4个回答

20
  • 缩小后会减少一个字符。
  • ! 应该处理其他 JavaScript 代码在此之前被连接且没有尾分号的情况。

差别不大。你应该使用自己更熟悉的方式。你可能需要在示例的开头加上一些内容以避免...

base.js

var lol = function() {
   alert(arguments[0]);
}

im-concat-to-base.js

(function() {
    // Irrelevant.
})();

jsFiddle前加上分号就能正常工作了...

jsFiddle.

...或者像 Twitter Bootstrap 一样,在前面加上感叹号!

jsFiddle.


14

它们都是解决语法歧义的方式。两种方式并没有更“hacky”的区别,只是一种风格选择。

你也可以这样做:

0 + function( $ ) {
  // ...
} ( window.jQuery || window.ender );

或者:

parseInt(function( $ ) {
  // ...
} ( window.jQuery || window.ender ) );

14
如果有人这样使用 parseInt(),我会非常困惑 :P - alex
我也是!关键是原问题中的两个选项代表了众多可能性中较不奇怪的选择 :-) - Pointy
@Pointy 两者都不比另一个更“hacky” => 你的意思是两者都是hack,而不是常规的js表示法吗? - Christophe
4
它们都是“常规”JavaScript习语。重点在于,在任何 JavaScript表达式中,函数的实例化只是一件可以做的事情。 - Pointy

3

在判断 !undefined 的步骤中,您也可以使用 void 运算符来消除歧义:

void function($) {
     ...
}(window.jQuery || window.ender);

这有点C语言的质感 ;-)


1

我还没有看到的一个答案是,使用这种方式可以避免将整个函数用括号包围起来。除了审美考虑之外,这对于一些编辑器来说可能是一个优点,因为它们使用括号来确定一行缩进的级别。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接