Not sure if what I want is possible but I am trying to create an enum in which each member has its own inner class. These inner classes will all have the same name Context
but will be implemented individually.
Ideally I would like them to be usable as such:
private handleType (MyEnum type) {
switch (type) {
case ENUM_VAL1:
MyEnum.ENUM_VAL1.Context context = new MyEnum.ENUM_VAL1.Context();
handleContext1(context);
break;
case ENUM_VAL2:
MyEnum.ENUM_VAL2.Context context = new MyEnum.ENUM_VAL1.Context();
handleContext2(context);
break;
case ENUM_VAL3:
MyEnum.ENUM_VAL3.Context context = new MyEnum.ENUM_VAL1.Context();
handleContext3(context);
break;
default:
break;
}
Open to other way of implementing this. But basically I need a switchable enum where each member has a "value" (1,2,3...) and also a means of associating said enums with a unique class with constructor.
EDIT: Some background. This is to be used between two services who communicate via JSON http requests. The requests will contain some metadata, one field of which is an integer that maps to the enum. The context is a POJO, but is different for each ENUM_VALUE. Essentially, the context will be constructed and serialized into JSON. This json will effectively be just a String field called context within the top level json request. On the receiving service, there will be a switch on ENUM_VALUE, where the context is decoded appropriately and then dispatched to its appropriate handler.
EDIT2: This enum will be shared between the two services.
EDIT3: Here is a more explicit explanation of what I am attempting to do.
MyServiceRequest:
public class MyServiceRequest {
String meta1;
String meta2;
int typeID;
String context;
}
generating request:
MyServiceRequest req = new MyServiceRequest();
req.meta1 = ...
req.meta2 = ...
req.typeID = MyEnum.ENUM_VALUE.getCode(); // int
MyEnum.ENUM_VALUE.Context context = new MyEnum.ENUM_VALUE.Context(); // factory would be fine as well
... // populate context
req.context = toJSON(context);
requestJSON = toJSON(req);
post(requestJSON);
decoding request:
MyServiceRequest req = ...
MyEnum type = new MyEnum(req.typeID);
switch(type) {
case ENUM_VALUE:
MyEnum.ENUM_VALUE.Context context = fromJSON(req.context, MyEnum.ENUM_VALUE.Context.class);
doSomething(context);
Yes, we can define an enumeration inside a class. You can retrieve the values in an enumeration using the values() method.
Each enum constant becomes a static final constant within that class. Then, an array $VALUES is created with all of the enum constants, in order of declaration. You can disassemble the code using the command javap -p -c Ordinals (on the compiled . class file) to find out the details.
An enum type is a special data type that enables for a variable to be a set of predefined constants. The variable must be equal to one of the values that have been predefined for it. Common examples include compass directions (values of NORTH, SOUTH, EAST, and WEST) and the days of the week.
Inner Classes As with instance methods and variables, an inner class is associated with an instance of its enclosing class and has direct access to that object's methods and fields. Also, because an inner class is associated with an instance, it cannot define any static members itself.
One think you could do instead is have your enum implement Supplier<Context>
. Now each item would have to declare a get() method to create the individual Context sub type.
enum MyEnum implements Supplier<Context>{
FOO{ @Override public Context get(){ return new FooContext(); } },
BAR{ @Override public Context get(){ return new BarContext(); } }
}
which would make your client code much simpler:
private void handleType (MyEnum type) {
handleContext(type.get());
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With