2012-10-10 142 views
3

为什么这个返回语法错误:功能包裹在括号

function(foo){console.log(foo)} 

我期望这个返回函数的值,因此返回其自身,而不是将其分配到任何东西,但我得到一个“语法错误:意外的令牌(”

但这个工程:

(function(foo){console.log(foo)}) 

请解释一下这些包装括号起什么作用我已经告诉括号是用来“增加可读性”,但在T他的情况肯定有更多的目的。

你可以请进入有关使用about()的更多细节吗?假设你将这段代码翻译成散文,那么()读起来会怎样?我也在向其他人描述这个概念,并且需要传递它的含义,以便每个人都能理解它。我试图回答的问题是()的含义是什么?他们有语义价值吗?它是什么?

+0

在第一个例子中缺少一个标识符。在第二个例子中,当你用parens包裹时,你正在创建一个表达式函数 – fcalderan

回答

6

你的第一个例子是一个功能声明 。它没有标识符,这是一个语法错误。这里的grammar for a function declaration(注意:标识符是不可选):

FunctionDeclaration :

functionIdentifier(FormalParameterListopt) {FunctionBody}

的括号包裹它,你把它变成一个功能表达(匿名的)。您可以通过后添加一对调用括号的执行:

(function(foo){console.log(foo)})("hello"); //Will log 'hello' 

下面是一个函数表达式的gammar(即现在的标识是可选的):

FunctionExpression :

functionIdentifieropt(FormalParameterListopt) {FunctionBody}


括号如何转将函数声明转换为函数表达式

在这种情况下,括号被解析为“grouping operator“。对于分组运算符的语法如下:

PrimaryExpression :

(Expression)

分组操作只能包含一个表达式,所以你的函数解析为一个表达式,而不是一个声明(很明显,在你的确切例如,函数可以”由于它没有标识符,所以是一个声明)。

+0

谢谢詹姆斯!但是我仍然错过了关于()的部分。他们似乎拥有神奇的力量,能够改变行动的优先级(1 + 1)* 2并能够将声明改为表达。我如何区分这两种情况?有没有放弃特征,或者这是如何工作的? – DLeonardi

+0

@ user436118 - 不客气:)查看我的编辑,我添加了一些关于括号如何将声明转换为表达式的内容。 –

+0

+1美丽的解释 – techfoobar

2

这是因为如果没有(),所述function(){}线是function declaration,而()expression

函数声明是一个奇怪的野兽,他们取得了他们在执行代码所限定的范围随处可见,所以像这样的片断工作:

foo(); 
function foo() { console.log('foo'); } 
+0

检查标题标题为“关于围绕圆括号的问题”的部分 http://dmitrysoshnikov.com/ecmascript/chapter-5-functions/#question-约括号括号] – complex857