好吧,我知道 FunctionDeclaration
和 FunctionExpression
之间有什么区别。 @ CMS做了great job解释。直到最近,我曾使用相同的语法在Douglas Crockford's示例后创建 lambda表达式和名称空间:
(function () {
"use strict";
}());
他将此convention证明如下:
当要立即调用函数时,整个调用表达式应该包含在parens中,以便明确生成的值是函数的结果,而不是函数本身。
此语法非常适合 lambda表达式,因为它们返回一个值。但是,名称空间不会返回值。因此,我现在更喜欢使用名称空间的以下语法(取自JavaScript Garden):
(function () {
"use strict";
})();
使用此语法的基本原理如下:
( // evaluate the function inside the paranthesis
function() {}
) // and return the function object
() // call the result of the evaluation
对命名空间使用此语法对我更有意义,因为:此语法将命名空间和调用分开;和Douglas Crockford's语法期望函数返回一个值。
但是,当我通过JSLint传递此语法时,我收到一条错误,指出“Move the invocation into the parens that contain the function.
”。我不明白为什么它会抱怨这种语法。这是一种广泛使用和接受的语法。
我打算通知Douglas Crockford这个问题。但是,在我这样做之前,我将非常感谢您提供的任何反馈。也许最好简单地坚持他的语法?请解释你的观点。
答案 0 :(得分:1)
回想起来,我相信克罗克福德的观点只是教条。他说:
当要立即调用函数时,整个调用表达式应该包含在parens中,以便明确生成的值是函数的结果,而不是函数本身。
我的论点是,当一个函数被立即调用时,如何产生的值不是函数的结果而不是函数本身?考虑:
产生的价值是功能:
var f = function () {
"use strict;"
};
正在生成的值是函数的结果:
var x = (function () {
"use strict;"
})();
如果您想要生成的值作为函数本身,那么就不要使用parens。无论如何使用它们都没有意义。
可以理解的是,有许多程序员仍然会在将函数表达式赋值给变量之前将其包装在括号中,或者谁会成为一个虐待狂并做这样的事情来混淆Doug:
var x = function () {
"use strict;"
}();
然而,了解发生了什么有多困难?也许在最后一个例子中,您需要向下滚动数百行代码才能找到,但是一个优秀的程序员可以省去其他人的麻烦,只需将函数包装在parens中;或者如果他是一个守财奴:
var x = ~function () {
"use strict;"
}();
除此之外,我甚至不会费心阅读那些一直想让我诅咒他的人写的代码。回到这个问题,虽然我真的不喜欢Crockford的语法是因为他将函数和调用分组在一个括号中。对我来说,这相当于以下几点:
var x = (f());
function f() {
"use strict;"
}
显然,在parens中包含一个函数调用看起来有点愚蠢和冗余,但这就是我的想象,它总是让我烦恼,但每个人都以他自己的方式。我个人认为我的语法看起来更清晰。