通过测试我发现了,
这不合法:
for (int i= 0; i < 1000000000; i++)
int j = i & i+1 ; // j cannot be declared here!
但这是:
for (int i= 0; i < 1000000000; i++) {
int j = i & i+1 ;
}
为什么?
答案 0 :(得分:16)
局部变量声明需要在一个块中。在第一种情况下,您没有在一个块中。在第二种情况下,j
在一个区块内,因此它是合法的。
局部变量声明不是语句,它是局部变量声明语句。从下面的引用中,局部变量声明只能作为块中的语句出现。 (块是一对包含语句和声明的花括号。)
for (int i= 0; i < 1000000000; i++)
int j = i & i+1 ; // Local variable j declaration not within a block ==> ERROR
for (int i= 0; i < 1000000000; i++) {
int j = i & i+1 ; // Local variable j declaration within a block ==> NO ERROR
}
引自14.4. Local Variable Declaration Statements:
...
每个局部变量声明语句都会立即包含 块。本地变量声明语句可以混合使用 与块中的其他类型的陈述一起自由。
...
来自14.2. Blocks:
块是一系列语句,本地类声明和 大括号内的局部变量声明语句。
Block: { BlockStatementsopt } BlockStatements: BlockStatement BlockStatements BlockStatement BlockStatement: LocalVariableDeclarationStatement ClassDeclaration Statement
通过执行每个局部变量来执行块 声明声明和其他声明按顺序从头到尾 最后(从左到右)。如果所有这些块语句都完成了 通常,然后块正常完成。如果其中任何一个阻止 语句因任何原因突然完成,然后块完成 突然出于同样的原因。
此外,这种行为并不仅限于Java。即使在C中,您也会在类似的情况下发现错误:
for(int i=0; i<=100; i++)
int j = i; /* Error: error: expected expression before 'int' */
for(int i=0; i<=100; i++) {
int j = i; /* Perfect */
}
答案 1 :(得分:12)
第一种方式不合法,因为编译器很清楚你不能使用你在那里声明的j
,因为你不能在{{1}内有另一个语句循环。基本上,在那个地方新的变量声明将超出下一个声明的范围,因此没有任何好处。
在第二种情况下,循环后面跟着括号,它会创建一个新的范围,你可以使用变量。
答案 2 :(得分:4)
对于允许单个语句而不是块的任何语法结构,不允许局部变量声明作为单个语句。所以for
,while
,if
等......
它崩溃的方式是(转述一点),你有for
statement:
for(...; ...; ...)Statement
阻止
ExpressionStatement
当您只有一个语句但ExpressionStatement
只有LocalVariableDeclarationStatement
时,可以使用BlockStatement
。
正如@RohitJain所指出的那样,仅将变量声明作为循环的单个语句并不是特别有用。