Подтвердить что ты не робот

Как получить имя Enum с помощью идентификатора?

У меня есть enum как:

public enum EnumStatus {

    PASSED(40L, "Has Passed"),
    AVERAGE(60L, "Has Average Marks"),
    GOOD(80L, "Has Good Marks");

    private java.lang.String name;

    private java.lang.Long id;

    EnumStatus(Long id, java.lang.String name) {
        this.name = name;
        this.id = id;
    }

    public java.lang.String getName() {
        return name;
    }

    public java.lang.Long getId() {
        return id;
    }
}

Мне нужно получить имена Enum (PASSED, AVERAGE, GOOD), используя только идентификаторы (40,60, 80). Как это сделать?

4b9b3361

Ответ 1

Создайте статический метод в enum, который ищет в values (неявный метод/член, не знает точно, что это такое) и возвращает соответствующее значение. Для случаев, когда метод не может найти подходящее значение, вы должны создать специальную запись, например. UNKNOWN, который вы можете вернуть. Таким образом, вам не нужно возвращать null, что всегда плохой идеей.

public static EnumStatus getById(Long id) {
    for(EnumStatus e : values()) {
        if(e.id.equals(id)) return e;
    }
    return UNKNOWN;
}

Btw - ваш код кажется неправильным. Скобка после GOOD, похоже, не принадлежит.

Ответ 2

Это можно сделать, используя статическую карту вместе со статическим инициализатором:

public enum EnumStatus {

    PASSED(40L, "Has Passed"),
    AVERAGE(60L, "Has Average Marks"),
    GOOD(80L, "Has Good Marks");

    private static final Map<Long, EnumStatus> byId = new HashMap<Long, EnumStatus>();
    static {
        for (EnumStatus e : EnumStatus.values()) {
            if (byId.put(e.getId(), e) != null) {
                throw new IllegalArgumentException("duplicate id: " + e.getId());
            }
        }
    }

    public static EnumStatus getById(Long id) {
        return byId.get(id);
    }

    // original code follows

    private java.lang.String name;

    private java.lang.Long id;

    EnumStatus(Long id, java.lang.String name) {
        this.name = name;
        this.id = id;
    }

    public java.lang.String getName() {
        return name;
    }

    public java.lang.Long getId() {
        return id;
    }

}

Это даст метод O(1) getById() и автоматически обнаружит, если у вас случайно есть дубликаты идентификаторов в перечислении.

Ответ 3

Вы делаете эту работу следующим образом:

public static String fromId(long id) {
        for (EnumStatus es : EnumStatus.values()) {
            if (es.id.equals(id)) {
                return es.getName();
            }
        }
        throw new IllegalArgumentException();
}

Ответ 4

Добавьте метод в свой Enum и получите его, передав идентификаторы.

 public static ArrayList<EnumStatus> getEnumStatusById(ArrayList<Long> idList) {
    ArrayList<EnumStatus> listById = new ArrayList();
    for(EnumStatus es: EnumStatus.values()) {
        if( idList.contains(es.getId())) {
            listById.add(es);
        }
    }
    return listById;
}

Ответ 5

public static EnumStatus getById(long id)
{
  for (EnumStatus e : EnumStatus.values())
  {
    if (id == e.getId()) return e;
  } 
  throw new IllegalArgumentException("oh no");
}

Ответ 6

Итерация по всем значениям и сравнение Id

for (EnumStatus  enumStatus : EnumStatus.values()) {
   if (..) {..}
}

Ответ 7

Иногда порядковый номер enum имеет четкую связь с этим типом идентификаторов, позволяя аккуратный способ получить O (1) в этих методах. В вашем коде ясно, что

EnumStatus.X = 40 + 20 * ordinal,

чтобы вы могли использовать статический массив который создается под капотами.

public static EnumStatus fromId(Long id) {
    int index = (id - 40L) / 20L;
    return values()[index];
}

Ответ 8

Определить контракт

/**
 * Contract that will allow Types with id to have generic implementation.
 */
public interface IdentifierType<T> {
  T getId();
}

Применить контракт

public enum EntityType implements IdentifierType<Integer> {
  ENTITY1(1, "ONE), ENTITY2(2, "TWO");

  private Integer id;
  private String name;

  private EntityType(int id, String name) {
    this.id = id;
    this.name = name;
  }

  public static EntityType valueOf(Integer id) {
    return EnumHelper.INSTANCE.valueOf(id, EntityType.values());
  }

  @Override
  public Integer getId() {
    return id;
  }
}

Помощник /Util

public enum EnumHelper {
  INSTANCE;

  /**
   * This will return {@link Enum} constant out of provided {@link Enum} values with the specified id.
   * @param id the id of the constant to return.
   * @param values the {@link Enum} constants of specified type.
   * @return the {@link Enum} constant.
   */
  public <T extends IdentifierType<S>, S> T valueOf(S id, T[] values) {
    if (!values[0].getClass().isEnum()) {
        throw new IllegalArgumentException("Values provided to scan is not an Enum");
    }

    T type = null;

    for (int i = 0; i < values.length && type == null; i++) {
        if (values[i].getId().equals(id)) {
            type = values[i];
        }
    }

    return type;
  }
}

Ответ 9

Если вы хотите сделать это для большего количества перечислений, я использую это:

public static T FindEnum<T>(long id) where T : struct
{
      return (T)Enum.ToObject(typeof(T), id);
}