I have switch case with 50 String checks in case as given below:
switch(str){
case "Employee number":
//setter
break;
}
I want to put them in Enum with description as given below:
enum myenum{
EMPLOYEE_NUMBER("Employee number"),
FIRST_NAME("First name");
private String desc;
private myenum(String desc) {
this.setDesc(desc);
}
public String getDesc() {
return desc;
}
public void setDesc(String desc) {
this.desc = desc;
}
}
Now, From Source i am getting String "Employee Number" and i want to write switch case in such a way that we can compare description of enum with incoming string input in Case.
I tried some methods in enum
myenum.valueOf(a); // This return enum value but not parameter
myenum.values // This is array which is also not useful here
Kindly suggest how it is achievable in Enum? I am using Java 8
and also suggest Is enum right choice here? or shall i create Static string class with all 50 values or any other best wayout?
You can first get the MyEnum
instance from String str
and then use switch
by MyEnum
, like below:
enum MyEnum {
EMPLOYEE_NUMBER("Employee number"),
FIRST_NAME("First name");
private String desc;
MyEnum(String desc) {
this.desc = desc;
}
public String getDesc() {
return desc;
}
public static Optional<MyEnum> fromDesc(String desc) {
return Stream.of(MyEnum.values()).filter(myEnum -> myEnum.getDesc().equals(desc)).findFirst();
}
}
And then in your main code:
Optional<MyEnum> maybeMyEnum = MyEnum.fromDesc(str);
if (maybeMyEnum.isPresent()) {
switch(maybeMyEnum.get()){
case EMPLOYEE_NUMBER:
//setter
break;
}
}
UPD 1:
As @Ole V.V. - stated in a comment, using Optional.get()
and Optional.isPresent()
is not a best practice - the idea is - you have to defer getting value out of Optional
as much as possible. Also Optional.get()
violates getter
contract:
Optional.get() is an "attractive nuisance" and is too tempting for programmers, leading to frequent errors. People don't expect a getter to throw an exception.
From JDK-8140281 : (opt) add no-arg orElseThrow() as preferred alternative to get()
So given that, you can rewrite your code as:
...
MyEnum.fromDesc(str)
.ifPresent(SomeClass::methodWithSwitchStatement);
...
class SomeClass {
public static void methodWithSwitchStatement(MyEnum myEnum) {
switch(myEnum){
case EMPLOYEE_NUMBER:
//setter
break;
}
}
}
...
The names in the above code are just for examples - you shouldn't use such names in your project.
UPD 2:
Here is the version of MyEnum
with caching:
enum MyEnum {
EMPLOYEE_NUMBER("Employee number"),
FIRST_NAME("First name");
private static final Map<String, MyEnum> cacheByDesc;
static {
cacheByDesc = Stream.of(MyEnum.values()).collect(Collectors.toMap(MyEnum::getDesc, e -> e));
}
private String desc;
MyEnum(String desc) {
this.desc = desc;
}
public String getDesc() {
return desc;
}
public static Optional<MyEnum> fromDesc(String desc) {
return Optional.ofNullable(desc)
.map(cacheByDesc::get);
}
}