7

有没有办法将枚举转换为常量表达式?我希望我的 switch 运算符在枚举的值中进行选择,但是我得到了一个编译错误“case 表达式必须是常量表达式”,所以我尝试在一个变量中声明它:

final int REG = MyEnum.REG.getIndex().intValue();

switch (service.getIndex()) {

case REG:

但我仍然得到同样的错误。根据甲骨文的文档http://docs.oracle.com/javase/specs/jls/se7/html/jls-15.html#jls-15.28

编译时常量表达式是表示原始类型值或字符串的表达式,它不会突然完成并且仅使用以下内容组成:

•原始类型的文字和字符串类型的文字

所以它不起作用,因为我没有使用文字。我想我必须将其声明为:

final int REG = 8;

但是将它链接到枚举会更好。有没有办法做到这一点?

编辑

原来我不需要使用任何最终变量。它很简单:

switch (service) {

case REG:

直到我看到安德里亚的评论,我才想到。感谢您的回答。

4

2 回答 2

6

If possible, modify your getIndex() method so that it returns an enum instead of an integer. If this is not possible, you need to map the index to an enum element:

Given the following enum:

public enum Index {
   ONE,
   TWO,
   THREE
}

you can map your index to an enum element by using

Index.values()[index]

Given your method Integer getIndex(), you can then do something like

switch(Index.values()[getIndex()])
    case ONE : ... 
       break;

    case TWO : ...
       break;

    case THREE : ...
       break;
}

Note that this might throw an ArrayIndexOutOfBoundsException if you try to access an index within the enum which is larger than the number of enum elements (e.g. in the sample above, if getIndex() returns a value > 2).


I would encapsulate the expression Index.values()[getIndex()] into an enum method like valueOf(int index), similar to the default valueOf(String s). You can then also handle the valid array index check there (and for example return a special enum value if the index is out of range). Similarly, you can then also convert discrete values which have special meanings:

public enum Index {
   ZERO,
   ONE,
   TWO,
   THREE,
   REG,
   INVALID;


   public static Index valueOf(int index) {

       if (index == 8) {
          return REG;
       }

       if (index >= values().length) {
          return INVALID;
       }

       return values()[index];
   }
}

This is an example only - in any case, it generally depends on the range of values you get from your getIndex() method, and how you want to map them to the enum elements.

You can then use it like

switch(Index.valueOf(service.getIndex())) {
   case ZERO : ... break;
   ...
   case REG : ... break;
   ...
}

See also Cast Int to enum in Java for some additional information (especially the hint that values() is an expensive operation since it needs to return a copy of the array each time it is called).

于 2013-05-08T10:40:30.830 回答
2

如果您想要分配给枚举常量的特定数值,请像这样

enum MyReg {
    REG(8), OTHER(13);

    public final int value;
    MyReg(int value) {
        this.value=value;
    }
}

然后你像这样使用它:

class Test { 
    public static void main(String[] args) {
        MyReg reg = MyReg.REG;
        switch (reg) {
        case OTHER:
            System.out.println(reg.value);
            break;
        case REG:
            System.out.println(reg.value);
            break;
        }
    }
}
于 2013-05-08T10:45:55.847 回答