break 和 switch 似乎执行所有 case 语句
在 Java 和 Eclipse (Kempler) 的最新稳定版本中,输入以下代码并执行,假设包名和类名存在:
In the latest stable release of Java and Eclipse (Kempler), entering the following code and executing it, assuming the package and class names exist:
package some_package;
public class what_the_heck {
public static void main(String[] args) {
int p = 2;
int x = 1;
switch(p){
case (1):
x--;
case (2):
x = 2;
case (3):
x = 3;
default:
x++;
}
System.out.println(x);
}
}
这会打印值 4.本来我认为它应该打印 2,因为我认为即使没有 break 语句,每段代码仍然保存在一个 case 语句中.现在我认为问题在于它是如何编译的.例如,我目前的信念是,在内部,布尔值会跟踪 case 语句是否等于该值.如果是,则布尔值为真,所有 case 语句都将被视为真,直到找到中断.这是有道理的,但我仍然想知道这背后是否还有其他原因,或者我的假设是否完全错误.
This prints the value 4. Originally, I thought it should print 2 because I thought that even if there were no break statements, each piece of code is still held in a case statement. Now I think that the issue lies in how it is compiled. For example, my current belief is that internally a boolean keeps track of whether or not a case statement was equal to the value. If it was, then the boolean is true and all case statements will be treated as true until a break is found. This makes sense, but I am still wondering if there are other reasons behind this, or if I am entirely wrong in my assumption.
推荐答案
switch之所以会这样,是因为:
The reason why switch works as it does is that this:
switch(p){
case (1):
x--;
case (2):
x = 2;
case (3):
x = 3;
default:
x++;
}
实际上只是这个的语法糖(基本上):
is really just syntactic sugar for this (basically):
if (p == 1)
goto .L1;
else if (p == 2)
goto .L2;
else if (p == 3)
goto .L3;
else
goto .L4;
.L1:
x--;
.L2:
x = 2;
.L3:
x = 3;
.L4:
x++;
Java 没有 goto
语句,但 C 有,这就是它的来源.因此如果 p
为 2,它会跳转到 .L2
并执行该标签后面的所有语句.
Java doesn't have a goto
statement, but C does, and that's where it comes from. So if p
is 2, it jumps to .L2
and executes all the statements following that label.
相关文章