96 votes

Obtention d'un enum associé à une valeur int

Auparavant, mes enums LegNo étaient définis simplement comme suit :

NO_LEG, LEG_ONE, LEG_TWO

et en appelant return LegNo.values()[i]; j'ai pu obtenir la valeur associée à chaque enum.

Mais maintenant j'ai décidé que je voulais le LegNo enum NO_LEG pour être l'int -1 au lieu de 0 J'ai donc décidé d'utiliser un constructeur privé pour initialiser et définir sa valeur int.

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

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

la seule chose maintenant est que, parce que je le fais de cette façon, la values() ne fonctionnera pas pour la méthode NO_LEG enum. Comment puis-je obtenir l'enum associé à l'int ? Existe-t-il un moyen efficace de le faire, autre que l'utilisation d'une instruction de commutation de cas ou d'un if-elseif-elseif ?

Je vois que beaucoup de questions de l'OS concernent l'obtention de la valeur int de l'enum, mais je cherche l'inverse.

156voto

adarshr Points 25912

EDIT août 2018

Aujourd'hui, je le mettrais en œuvre comme suit

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();
    }
}

Vous devrez maintenir un mappage à l'intérieur de l'enum.

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);
    }
}

Le bloc statique ne sera invoqué qu'une seule fois, de sorte qu'il n'y a pratiquement aucun problème de performance ici.

EDIT : Renommer la méthode en valueOf car elle est plus conforme aux autres classes Java.

25voto

Mike Adler Points 1179

Vous pouvez également inclure une méthode statique dans l'enum qui parcourt tous les membres et renvoie le bon.

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?");
   }
}

Maintenant, si vous voulez obtenir une valeur Enum par l'entier, il suffit d'utiliser :

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

18voto

Marcin Points 104

La réponse d'adarshr adapté à 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);
    }
}

14voto

Tadeas Points 121

Vous pouvez également accéder à la valeur de l'enum correspondant à une valeur entière donnée en appelant la méthode values() sur l'enum LegNo. Elle renvoie le champ de l'enum LegNo : LegNo.values()[0]; //returns LEG_NO LegNo.values()[1]; //returns LEG_ONE LegNo.values()[2]; //returns LEG_TWO

Ce n'est pas exactement ce qu'il cherchait, mais c'est assez proche et très simple. (Bien que le sujet soit mort, il pourrait être utile à quelqu'un d'autre).

6voto

Dmitry Sokolyuk Points 155

Façon Java 8 avec valeur par défaut :

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);
    }
}

à appeler :

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

ou avec Exception :

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

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