Java 通用枚举作为参数

Dar*_*man 3 java generics enums

所以我有几个如下定义的枚举。我有一个使用枚举来查找值的方法。

public enum MyEnum1
{
   STRING1("My String1"),
   STRING2("My String2"),
   STRING3("My String3"),
   STRINGLESS("String not found");

   private String s;

   private MyEnum1(String s) { this.s = s; }

   public String getValue() { return s; }
}

public enum MyEnum2
{
   STRING1("My String1"),
   STRING2("My String2"),
   STRING3("My String3"),
   STRINGLESS("String not found");

   private String s;

   private MyEnum2(String s) { this.s = s; }

   public String getValue() { return s; }
}

public class MyClass1
{
    public static String getPlacement(String myString)
    {
        for (MyEnum1 a: MyEnum1.values())
            if (myString.contains(a.toString()))
                return a.getValue();

        return MyEnum1.STRINGLESS.getValue();
     }
}

public class MyClass2
{
    public static String getPlacement(String myString)
    {
        for (MyEnum2 a: MyEnum2.values())
            if (myString.contains(a.toString()))
                return a.getValue();

        return MyEnum2.STRINGLESS.getValue();
     }
}
Run Code Online (Sandbox Code Playgroud)

现在我定义了 5 个枚举,它们都由相同的 getPlacement 方法处理,但我必须使用 MyEnum2、MyEnum3... 创建 5 个不同的 MyClass 类(MyClass2、MyClass3...),并在 For 循环中硬编码才能实现这一点。

我试过了...

public static String getPlacement(Enum e, String myString) {}
Run Code Online (Sandbox Code Playgroud)

public static String getPlacement(Enum<?> e, String myString) {}
Run Code Online (Sandbox Code Playgroud)

但两者都不起作用。

我想将 Enum 作为参数传递给 getPlacement 方法,从而允许我只有一个 MyClass 类可以处理 5 个不同的 Enum。这可能吗?

Rad*_*def 6

为了保留 的确切语义getPlacement,您可以这样做:

interface StringValue {
    String getValue();
}

enum MyEnum1 implements StringValue {
    ...
    private String stringValue;
    ...

    @Override
    public String getValue() {
        return stringValue;
    }
}

static <E extends Enum<E> & StringValue>
String getPlacement(Class<E> enumClass, String inValue) {
    for(E constant : enumClass.getEnumConstants()) {
        if(inValue.contains(constant.toString()))
            return constant.getValue();
    }
    return Enum.valueOf(enumClass, "STRINGLESS").getValue();
}
Run Code Online (Sandbox Code Playgroud)

我不确定这里的确切语义对您是否真的很重要。如果不是,还有更简单的方法。如果你不需要,contains你可以直接使用Enum#valueOf. 如果您可以覆盖toString(因为您也可以使用Enum#name),那么您不需要接口。

而且,就像所有使用枚举的复杂情况一样,如果您不使用枚举,事情可能会简单得多。final具有私有构造函数和常量的类可以public static final做许多枚举不能做的事情(例如从抽象超类型继承......)。