Is it possible use a class name in java switch/case statement?

22,430

Solution 1

The compiler error already says it. The case labels must be constant expressions and neither, class literals nor the result of invoking getSimpleName() on them, are constant expressions.

A working solution would be:

String tableName = "MyClass1";
...
switch (tableName) {
    case "MyClass1":
        return 1;
    case "MyClass2":
        return 2;
    default:
        return Integer.MAX_VALUE;
}

The expression MyClass1.class.getSimpleName() is not simpler than "MyClass1", but, of course, there won’t be any compile-time check whether the names match existing classes and refactoring tools or obfuscators don’t notice the relationship between the class MyClass1 and the string literal "MyClass1".

There is no solution to that. The only thing you can do to reduce the problem, is to declare the keys within the associated class to document a relationship, e.g.

class MyClass1 {
    static final String IDENTIFIER = "MyClass1";
    ...
}
class MyClass2 {
    static final String IDENTIFIER = "MyClass2";
    ...
}
...
String tableName = MyClass1.IDENTIFIER;
...
switch (tableName) {
    case MyClass1.IDENTIFIER:
        return 1;
    case MyClass2.IDENTIFIER:
        return 2;
    default:
        return Integer.MAX_VALUE;
}

This documents the relationship to the reader, but tools still won’t ensure that the actual string contents matches the class name. However, depending on what you want to achieve, it might become irrelevant now, whether the string contents matches the class name…

Solution 2

Instead of using a switch, why not store the mappings in a map?

Create a map of String to Integer, and map all the class names to their return value.

On a request, if the entry does not exist, return the default value. Otherwise, return the value in the map.

Solution 3

Instead of Switch..case why don't you use If..Else. Should work in all versions of java till i know.

if (tableName.equals(MyClass1.class.getSimpleName())) {
     return 1;
} else if (tableName.equals(MyClass2.class.getSimpleName())) {
     return 2;
} else {
     return Integer.MAX_VALUE;
}
Share:
22,430
dedek
Author by

dedek

Text processing in Java with Gate and Treex for Datlowe sourceforge - github - linkedin - researchgate

Updated on July 09, 2022

Comments

  • dedek
    dedek almost 2 years

    I would like to use a java switch statement, which uses class names as case constants. Is it possible somehow? Or do I have to duplicate the class names?

    Following code does not work because of compiler error:

    case expressions must be constant expressions

    String tableName = "MyClass1";
    
    ...
    
    switch (tableName) {
    case MyClass1.class.getSimpleName():
        return 1;
    case MyClass2.class.getSimpleName():
        return 2;
    default:
        return Integer.MAX_VALUE;
    }
    

    Here is a online demonstration of the issue (openjdk 1.8.0_45): http://goo.gl/KvsR6u