我只是被这种行为所咬住,谷歌搜索时出现了这个问题。我以为我会分享发现的一些额外信息。
每次在枚举上使用开关时,javac 1.5和1.6都会创建一个附加的综合类。该类包含一个所谓的“交换映射”,它将枚举索引映射到交换表跳转编号。重要的是,为发生切换的类(而不是枚举类)创建综合类。
这是生成的示例:
枚举类
public enum EnumClass { VALUE1, VALUE2, VALUE3 }
EnumUser.java
public class EnumUser {
public String getName(EnumClass value) {
switch (value) {
case VALUE1: return "value 1";
case VALUE3: return "value 3";
default: return "other";
}
}
}
综合EnumUser $ 1.class
class EnumUser$1 {
static final int[] $SwitchMap$EnumClass = new int[EnumClass.values().length];
static {
$SwitchMap$EnumClass[EnumClass.VALUE1.ordinal()] = 1;
$SwitchMap$EnumClass[EnumClass.VALUE3.ordinal()] = 2;
};
}
然后,此开关映射用于为lookupswitch
或tableswitch
JVM指令生成索引。它将每个枚举值转换为从1到[转换案例数]的对应索引。
EnumUser.class
public java.lang.String getName(EnumClass);
Code:
0: getstatic #2;
3: aload_1
4: invokevirtual #3;
7: iaload
8: lookupswitch{
1: 36;
2: 39;
default: 42 }
36: ldc #4;
38: areturn
39: ldc #5;
41: areturn
42: ldc #6;
44: areturn
tableswitch
如果存在三个或更多切换案例,则使用,因为它执行lookupswitch
的线性查询比线性搜索更有效的恒定时间查找。从技术上讲,javac可以在使用综合开关映射时忽略整个业务lookupswitch
。
推测:我手头没有Eclipse的编译器要进行测试,但我想它不会对合成类造成困扰,而只是使用lookupswitch
。或者,可能需要比原始“问询者”进行“ ugprades”测试之前更多的转换案例tableswitch
。