Java中带有负数/间隔值的枚举

3

我在Java中遇到了枚举问题。我有一个从-1开始的枚举:

    public enum AipType {
        Unknown(-1),
        None(0),
        AipMod(1),
        AipNoMod(2);

        private final int id;
        AipType(int id) {this.id = id;}
        public int getValue() {return id;}
    }

问题出现在我使用这段代码来初始化一个 AipType 变量时。
AipType at = AipType.getValues()[index];

其中index是区间[-1,0,1,2]中的一个数字,-1会破坏值。例如,0返回Unknown,1返回AipMod,2返回AipNoMod。

我使用了这个实现,因为我需要手动设置每个枚举案例的数值。在其他情况下,我有一个值之间的间隙,所以我有同样的问题:我不能使用values(),然后用[]访问。

我尝试以这种方式初始化

AipType at = AipType(index);

但是它不起作用。

有什么想法吗?谢谢...


AipType.getValues()[index + 1];也许? - Andrei Nicusan
在其他情况下,我有一个值之间的间隙。这是一个天真的解决方案,只适用于这种情况。我正在寻找一个始终有效的解决方案... - Fry
好的,那就看一下作为答案发布的解决方案。它们都看起来不错。几乎完美 :) - Andrei Nicusan
5个回答

7
我们不知道你正在使用的 getValues() 方法究竟是做什么的。它是否应该是 values()
无论如何,您可以在您的enum中添加一个static方法,返回该值的正确enum实例,并在需要时调用它:
public enum AipType {
    Unknown(-1),
    None(0),
    AipMod(1),
    AipNoMod(2);

    private final int id;
    AipType(int id) {this.id = id;}
    public int getValue() {return id;}

    public static AipType fromValue(int id) {
        for (AipType aip: values()) {
            if (aip.getValue() == id) {
                return aip;
            }
        }
        return null;
    }
}

如果你经常调用fromValue(),你可能还想在enum内部缓存values()返回的数组并使用它。或者更好的做法是使用一个map

6

不要使用values(),而是使用Map<Integer, AipType>,并通过方法公开访问:

public enum AipType {
    UNKNOWN(-1),
    NONE(0),
    MOD(1),
    NO_MOD(2);

    private static final Map<Integer, AipType> VALUE_TO_ENUM_MAP;
    private final int value;

    static {
        VALUE_TO_ENUM_MAP = new HashMap<>();
        for (AipType type : EnumSet.allOf(AipType.class)) {
            VALUE_TO_ENUM_MAP.put(type.value, type);
        }
    }

    private AipType(int value) {
        this.value = value;
    }

    public int getValue() {
        return id;
    }

    public static AipType forValue(int value) {
        return VALUE_TO_ENUM_MAP.get(value);
    }
}

这将完全灵活地处理值,或者您仍然可以使用数组并适当偏移它。


5
Enum.getValues()返回基于枚举类定义顺序的枚举数组。 getValues()不知道您在枚举中添加的id字段或getValue()方法。
你可以通过添加一个静态函数来代替调用getValues()[-1](顺便说一下,在Java中永远无法使用-1索引数组),如下所示:
static AipType getAipType(int id) {
    for (AipType a : getValues()) {
        if (a.getId() == id) return a;
    }
    throw new IllegalArgumentException("id=" + id + " does not exist");
}

1
你能像下面这样声明你的枚举吗?
public enum AipType {
    Unknown(-1),None(0),AipMod(1),AipNoMod(2);
    private int value;

    private AipType(int value) {
        this.value = value;
    }
    public int getValue() {
        return this.value;
    }

    public static AipType fromValue(int value) {
        for (AipType at: values()) {
            if (at.getValue() == value) {
                return at;
            }
        }
        return null;
    }
};  

并实例化如下:

AipType at = AipType.fromValue(-1);

0
如果id是完全自定义的,你唯一的机会就是创建一个映射表,并在那里存储id->AipType的映射关系。
示例:
public enum AipType {
  ... //enum definitions here

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

  static {
    for( AipType a : AipType.values() ) {
      map.put(a.id, a);
    }
  }

  public static AipType typeById( int id ) {
    return map.get(id);
  }
}

然后像这样调用:AipType.typeById(-1);

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接