检查枚举类型是否包含给定名称的常量

Bug*_*ray 7 java generics enums

我的代码中有多个枚举:

public enum First { a, b, c, d; }

public enum Second { e, f, g; }
Run Code Online (Sandbox Code Playgroud)

我想有一个方法,使用valueOf()检查任何枚举中是否存在值,而不为每个枚举类型写一个值.例如(此代码不运行):

public boolean enumTypeContains(Enum e, String s) {
    try {
        e.valueOf(s);
    } catch (IllegalArgumentException iae) {
        return false;
    }
    return true;
}
Run Code Online (Sandbox Code Playgroud)

用法:

enumTypeContains(First,"a"); // returns true
enumTypeContains(Second,"b"); // returns false
Run Code Online (Sandbox Code Playgroud)

关于如何做这样的事情的任何想法?

Paŭ*_*ann 10

这应该工作:

public <E extends Enum<E>> boolean enumTypeContains(Class<E> e, String s) {
    try {
        Enum.valueOf(e, s);
        return true;
    }
    catch(IllegalArgumentException ex) {
        return false;
    }
}
Run Code Online (Sandbox Code Playgroud)

然后你必须通过它来调用它

enumTypeContains(First.class, "a");
Run Code Online (Sandbox Code Playgroud)

我不确定是否只是简单地搜索值(比如来自jinguy的答案)可能比创建和抛出异常更快.这将取决于您将获得的频率false,您拥有的常数以及堆栈跟踪的持续时间(例如,调用它的深度).

如果您经常需要(对于相同的枚举),最好创建一次HashSet或HashMap将名称映射到枚举值.


jjn*_*guy 8

这是你的解决方案:

public static boolean contains(Class<? extends Enum> clazz, String val) {
   Object[] arr = clazz.getEnumConstants();
   for (Object e : arr) {
      if (((Enum) e).name().equals(val)) {
         return true;
      }
   }
   return false;
}
Run Code Online (Sandbox Code Playgroud)

它获取所有enum的vaules并检查它是否具有与您传入的参数共享名称的值.如果是,则返回true,否则返回false.

这已经过测试和运作.测试代码:

public class Test {
   public static void main(String[] args) {
      System.out.println(contains(Haha.class, "Bad"));
      System.out.println(contains(Haha.class, "Happy"));
      System.out.println(contains(Haha.class, "Sad"));
   }

   static enum Haha {
      Happy, Sad;
   }
}
Run Code Online (Sandbox Code Playgroud)

打印:

false
true
true
Run Code Online (Sandbox Code Playgroud)

  • 你可以通过使第一个参数`Class <?的类型在编译时将它限制为`enum`类型.扩展Enum <?>>`.然后,您不需要进行任何运行时检查. (3认同)