90 votes

Convertir une valeur entière en Java Enum correspondant

J'ai un enum comme ça:

 public enum PcapLinkType {
  DLT_NULL(0)
  DLT_EN10MB(1)
  DLT_EN3MB(2),
  DLT_AX25(3),
  /*snip, 200 more enums, not always consecutive.*/
  DLT_UNKNOWN(-1);
    private final int value;   

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

Maintenant, je reçois un int d’entrée externe et je veux l’entrée correspondante - le fait de lever une exception si une valeur n’existe pas est ok, mais de préférence, il serait de DLT_UNKNOWN dans ce cas.

 int val = in.readInt();
PcapLinkType type = ???; /*convert val to a PcapLinkType */
 

110voto

MeBigFatGuy Points 12489

Vous devez le faire manuellement en ajoutant une carte statique dans la classe qui mappe des entiers en énums, tels que

 private static final Map<Integer, PcapLinkType> intToTypeMap = new HashMap<Integer, PcapLinkType>();
static {
    for (PcapLinkType type : PcapLinkType.values()) {
        intToTypeMap.put(type.value, type);
    }
}

public static PcapLinkType fromInt(int i) {
    PcapLinkType type = intToTypeMap.get(Integer.valueOf(i));
    if (type == null) 
        return PcapLinkType.DLT_UNKNOWN;
    return type;
}
 

33voto

Il existe une méthode statique values() qui est documentée, mais pas celle que vous attendez: http://docs.oracle.com/javase/tutorial/java/javaOO/enum.html

 enum MyEnum {
    FIRST, SECOND, THIRD;
    private static MyEnum[] allValues = values();
    public static MyEnum fromOrdinal(int n) {return allValues[n];}
}
 

En principe, vous ne pouvez utiliser que values()[i] , mais il existe des rumeurs selon lesquelles values() créerait une copie du tableau chaque fois qu'il est appelé.

16voto

Bozho Points 273663

Vous devrez créer une nouvelle méthode statique dans laquelle vous itérerez PcapLinkType.values () et comparerez:

 public static PcapLinkType forCode(int code) {
    for (PcapLinkType typе : PcapLinkType.values()) {
        if (type.getValue() == code) {
            return type
        }
    }
    return null
 }
 

Ce serait bien si on l’appelle rarement. S'il est appelé fréquemment, examinez l'optimisation Map suggérée par d'autres.

11voto

Jack Gajanan Points 619

si vous avez énum comme ça

 public enum PcapLinkType {
  DLT_NULL(0)
  DLT_EN10MB(1)
  DLT_EN3MB(2),
  DLT_AX25(3),
  /*snip, 200 more enums, not always consecutive.*/
  DLT_UNKNOWN(-1);
    private final int value;   

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

alors vous pouvez l'utiliser comme

 PcapLinkType type = PcapLinkType.values()[1]; /*convert val to a PcapLinkType */
 

10voto

Esko Luontola Points 53877

Vous pouvez faire quelque chose comme ceci pour les enregistrer automatiquement dans une collection avec laquelle convertir facilement les entiers en enum correspondant. (En passant, il n'est pas permis de les ajouter à la carte dans le constructeur d'énum. C'est agréable d'apprendre de nouvelles choses même après plusieurs années d'utilisation de Java. :)

 public enum PcapLinkType {
    DLT_NULL(0),
    DLT_EN10MB(1),
    DLT_EN3MB(2),
    DLT_AX25(3),
    /*snip, 200 more enums, not always consecutive.*/
    DLT_UNKNOWN(-1);

    private static final Map<Integer, PcapLinkType> typesByValue = new HashMap<Integer, PcapLinkType>();

    static {
        for (PcapLinkType type : PcapLinkType.values()) {
            typesByValue.put(type.value, type);
        }
    }

    private final int value;

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

    public static PcapLinkType forValue(int value) {
        return typesByValue.get(value);
    }
}
 

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X