即时函数调用语法

2022-08-30 05:36:37

有一个JSLint选项,实际上是The Good Parts之一,“[需要]围绕即时调用进行parens”,这意味着构造

(function () {

  // ...

})();

相反,需要写成

(function () {

  // ...

}());

我的问题是 - 谁能解释为什么第二种形式可能被认为更好?它更有弹性吗?不易出错?与第一种形式相比,它有什么优势?


自从提出这个问题以来,我开始理解在函数值和函数值之间有清晰的视觉区别的重要性。考虑以下情况:立即调用的结果是赋值表达式的右侧:

var someVar = (function () {

  // ...

}());

尽管最外层的括号在语法上是不必要的,但左括号给出了一个前期指示,表明所分配的值不是函数本身,而是被调用函数的结果。

这类似于Crockford关于构造函数大写的建议 - 它旨在为任何查看源代码的人提供视觉提示。


答案 1

来自Douglas Crockford的风格约定指南:(搜索“立即调用”)

当要立即调用函数时,应将整个调用表达式包装在 parens 中,以便清楚地知道正在生成的值是函数的结果,而不是函数本身。

所以,基本上,他认为它更清楚地说明了函数值和函数值之间的区别。所以,这是一个风格问题,而不是代码本身的实质性差异。

更新的参考,旧的PPT不再存在


答案 2

立即调用的匿名函数将其包装在parens中,因为:

  1. 它们是函数表达式,省略parens会导致它被解释为函数声明,这是语法错误。

  2. 函数表达式不能以单词 function 开头。

  3. 将函数表达式赋给变量时,不返回函数本身,返回函数的返回值,因此 parens 计算其中的内容并生成一个值。当执行函数时,尾随 parens 导致函数立即执行。..}()