获取与int值关联的枚举

时间:2012-06-15 09:12:17

标签: java enums

以前,我将LegNo枚举定义为:

NO_LEG, LEG_ONE, LEG_TWO

并且通过调用return LegNo.values()[i];,我能够获得与每个枚举相关联的值。

但是现在我已经决定要LegNo枚举NO_LEG为int -1而不是0 所以我决定使用私有构造函数初始化并设置其int值

NO_LEG(-1), LEG_ONE(1), LEG_TWO(2);

private LegNo(final int leg) { legNo = leg; }

现在唯一的事情是,因为我这样做,values()方法不适用于NO_LEG枚举。如何获得与int关联的枚举?除了使用case switch语句或if-elseif-elseif

之外,还有其他有效的方法吗?

我可以看到很多关于从枚举中获取int值的问题,但是我正在反过来。

9 个答案:

答案 0 :(得分:132)

2018年8月编辑

今天我将实现如下

public enum LegNo {
    NO_LEG(-1), LEG_ONE(1), LEG_TWO(2);

    private final int value;

    LegNo(int value) {
        this.value = value;
    }

    public static Optional<LegNo> valueOf(int value) {
        return Arrays.stream(values())
            .filter(legNo -> legNo.value == value)
            .findFirst();
    }
}

你必须在枚举中维护一个映射。

public enum LegNo {
    NO_LEG(-1), LEG_ONE(1), LEG_TWO(2);

    private int legNo;

    private static Map<Integer, LegNo> map = new HashMap<Integer, LegNo>();

    static {
        for (LegNo legEnum : LegNo.values()) {
            map.put(legEnum.legNo, legEnum);
        }
    }

    private LegNo(final int leg) { legNo = leg; }

    public static LegNo valueOf(int legNo) {
        return map.get(legNo);
    }
}

静态块只会被调用一次,所以这里几乎没有性能问题。

编辑:将方法重命名为valueOf,因为它更符合其他Java类。

答案 1 :(得分:20)

您还可以在枚举中包含一个静态方法,该方法遍历所有成员并返回正确的方法。

public enum LegNo {
   NO_LEG(-1),
   LEG_ONE(1),
   LEG_TWO(2);

   private int legIndex;

   private LegNo(int legIndex) { this.legIndex = legIndex; }

   public static LegNo getLeg(int legIndex) {
      for (LegNo l : LegNo.values()) {
          if (l.legIndex == legIndex) return l;
      }
      throw new IllegalArgumentException("Leg not found. Amputated?");
   }
}

现在,如果您想通过整数获取Enum值,只需使用:

int myLegIndex = 1; //expected : LEG_ONE
LegNo myLeg = LegNo.getLeg(myLegIndex);

答案 2 :(得分:16)

adarshr's answer适用于Java 8:

import static java.util.Arrays.stream;
import static java.util.stream.Collectors.toMap;

import java.util.Map;

public enum LegNo {
    NO_LEG(-1), LEG_ONE(1), LEG_TWO(2);

    private final int legNo;

    private final static Map<Integer, LegNo> map =
            stream(LegNo.values()).collect(toMap(leg -> leg.legNo, leg -> leg));

    private LegNo(final int leg) {
        legNo = leg;
    }

    public static LegNo valueOf(int legNo) {
        return map.get(legNo);
    }
}

答案 3 :(得分:7)

您还可以通过调用enum LegNo上的values()方法来访问与给定整数值对应的Enum值。它返回LegNo枚举的字段: LegNo.values[0]; //returns LEG_NO LegNo.values[1]; //returns LEG_ONE LegNo.values[2]; //returns LEG_TWO

不是他正在寻找的东西,但非常接近但确实非常简单。 (虽然主题已经死了,但对其他人来说可能有用。)

答案 4 :(得分:6)

Java 8方式,默认值为:

public enum LegNo {
    NO_LEG(-1), LEG_ONE(1), LEG_TWO(2);

    private final int legNo;

    LegNo(int legNo) {
        this.legNo = legNo;
    }

    public static LegNo find(int legNo, Supplier<? extends LegNo> byDef) {
        return Arrays.asList(LegNo.values()).stream()
                .filter(e -> e.legNo == legNo).findFirst().orElseGet(byDef);
    }
}

致电:

LegNo res = LegNo.find(0, () -> LegNo.NO_LEG);

或使用例外:

LegNo res = LegNo.find(0, () -> {
    throw new RuntimeException("No found");
});

答案 5 :(得分:2)

public enum LegNo {

  NO_LEG(-1), LEG_ONE(1), LEG_TWO(2);

  private final int code;

  LegNo(int code) {
    this.code = code;
    ReverseStorage.reverseMap.put(code, this);
  }

  public static Optional<LegNo> getByCode(int code) {
    return Optional.ofNullable(ReverseStorage.reverseMap.get(code));
  }

  private static final class ReverseStorage {
    private static final Map<Integer, LegNo> reverseMap = new LinkedHashMap<>();
  }
}

答案 6 :(得分:1)

由于你的枚举只包含3个元素,最快的方法就是使用一系列if else,就像你建议的那样。

编辑:adarshr提供的答案更适合一般情况,其中有很多枚举值,但我认为这对你的问题来说太过分了。

答案 7 :(得分:0)

public enum LegNo {
    NO_LEG(-1), LEG_ONE(1), LEG_TWO(2);

    private int legNo;

    private LegNo(int leg) { legNo = leg; }

    public static LegNo valueOf(int legNo) {
        for (LegNo leg : LegNo.values()) {
            if (leg.legNo == legNo) return leg;
        }   
    }
}

assert LegNo.valueOf(2) == LegNo.LEG_TWO
assert LegNo.valueOf(3) == null

答案 8 :(得分:-4)

public enum body
{
    NO_LEG = 0,         // bit 1
    LEG_ONE = 2,        // bit 2 
    LEG_TWO = 4,        // bit 3 
    NO_ARM = 8,          // bit 4 
    ARM_ONE = 16,  // bit 5 
    ARM_TWO = 32  // bit 6 

}

像这样使用它    (int)body.LEG_ONE; ///返回2

这也非常快,并且易于阅读,因为它是在编译时完成的。