我有一些Java代码以两种方式使用花括号
// Curly braces attached to an 'if' statement:
if(node.getId() != null)
{
node.getId().apply(this);
}
// Curly braces by themselves:
{
List<PExp> copy = new ArrayList<PExp>(node.getArgs());
for(PExp e : copy)
{
e.apply(this);
}
}
outAMethodExp(node);
第一个if
语句后的那些独立花括号是什么意思?
答案 0 :(得分:116)
额外括号的唯一目的是提供范围限制。 List<PExp> copy
只会存在于这些大括号内,并且在它们之外没有范围。
如果这是生成的代码,我假设代码生成器执行此操作以便它可以插入一些代码(例如此代码),而不必担心插入List<PExp> copy
的次数而不必担心如果此片段多次插入同一方法,可能会重命名变量。
答案 1 :(得分:25)
我认为matt b写的是什么,我将补充说,我见过的匿名大括号的另一个用途是在匿名类中声明一个隐式构造函数。例如:
List<String> names = new ArrayList<String>() {
// I want to initialize this ArrayList instace in-line,
// but I can't define a constructor for an anonymous class:
{
add("Adam");
add("Eve");
}
};
一些单元测试框架已经将这种语法提升到了另一个层次,这确实允许一些看起来完全无法编译的光滑的东西。由于他们看起来不熟悉,我自己并不是一个很大的粉丝,但至少要认识到如果你遇到这种用途会发生什么事情。
答案 2 :(得分:7)
我同意范围限制答案,但会增加一件事。
有时你会在喜欢折叠代码部分的代码中看到类似这样的结构,并且编辑器会自动折叠括号。他们使用它来折叠逻辑部分中的代码,这些部分不属于函数,类,循环等通常会被折叠起来的。
答案 3 :(得分:4)
我实际上猜测有人忘记了其他声明。
很少有理由甚至打扰创建额外的块范围。在这种情况下,大多数情况下,有人可能忘记输入控制语句的可能性远远超过他们做一些聪明的事情。
答案 4 :(得分:2)
他们构成了内在的范围。在这些括号内声明的变量在它们之外是不可见的。这也适用于C / C ++。
答案 5 :(得分:1)
答案 6 :(得分:1)
大括号对缩小switch / case语句的范围也很有用。
switch(foo) {
case BAR:
int i = ...
...
case BAZ:
int i = ... // error, "i" already defined in scope
}
但你可以写
switch(foo) {
case BAR:{
int i = ...
...
}
case BAZ:{
int i = ... // OK
}
}
答案 7 :(得分:0)
我认为他们只是定义了一个未命名的范围级别。
答案 8 :(得分:0)
它们定义了一个新范围,这意味着在此范围内声明的所有内容在花括号外都不可见。
答案 9 :(得分:0)
带来范围,副本将不会在其外部显示,因此您可以稍后声明另一个具有相同名称的变量。退出该范围后,垃圾收集器就可以收集它。在这种情况下, copy 用作临时变量,因此这是一个很好的例子。
答案 10 :(得分:0)
作为一个有趣的说明:大括号实际上启用了一类语句:声明。
这是非法的:if(a) int f;
但这是合法的:if(a) { int f; }