Alex Rivera | Logout

Enums shared static look-up method

Asked 2012-04-12T10:43:42.807
31

I have the following Enum:

public enum MyEnum{
    A(10, "First"), //
    B(20, "Second"), //
    C(35, "Other options");

    private Integer code;
    private String description;

    private MyEnum(Integer code, String description) {
        this.code = code;
        this.description = description;
    }

    public Integer getCode() {
        return code;
    }

    public String getDescription() {
        return description;
    }

    public static MyEnum getValueOf(Integer code) {
        for (MyEnum e : MyEnum.values()) {
            if (e.getCode().equals(code)) {
                return e;
            }
        }
        throw new IllegalArgumentException("No enum const " + MyEnum.class.getName() + " for code \'" + code
                + "\'");
    }
}

Which works fine. The getValueOf-method exists because when communicating with an external partner, we only get the code (they chose) to map to. I need the description because I need to show a meaningfull phrase in the GUI.

But I now have a number of similar enum classes. All having their own code & description, and they need the same lookup functionality. I wanted the getValueOf-method to be generic so I don't need to support 30+ different enums for basically the same method.

To solve this I wanted to make an abstract class to define this method and implement some of the common logic but this is impossible because I can't extend Enum.

Then I tried to make a Utility class with the following method:

public static <T extends Enum<T>> T getValueOf(Enum<T> type, Integer code) {...}

But generics with Enums are confusing and I don't understand how to get this working.

Basically what I want to know is: What is a good approach to define a common utility to an enum?

Edit
Report

1 Answer

8

This is a bit tricky because the values() method is static. You would actually need reflection, but there is a nice way to hide this using standard library functionality.

First, define an interface with the methods common to all of your enum types:

public interface Common {
    Integer getCode();
    String getDescription();
}

Then, make all your enums implement this interface:

public enum MyEnum implements Common {...}

The static method you want to have then looks like:

public static <T extends Enum<T> & Common> T getValueOf( Class<T> type, Integer code ) {
    final EnumSet<T> values = EnumSet.allOf( type );
    for(T e : values) {
        if(e.getCode().equals( code )) {
            return e;
        }
    }
    throw new IllegalArgumentException( "No enum const " + type.getName() + " for code \'" + code + "\'" );
}
answered 2012-04-12T11:01:10.940

Your Answer