user1648409
user1648409

Reputation:

Get class instance from enum type

I have the Color enum with:

  1. RED

  2. BLUE

  3. GREEN

I also have these 3 classes:

  1. Red

  2. Blue

  3. Green

My Testclass uses the attribute private Color color and stores one enum value there. How can I return the corresponding class object when calling getValue() or something on private Color color?

Example: If my Testclass has color = Color.RED, it should return a new instance of the class Red when calling getValue() on it.

Upvotes: 2

Views: 9433

Answers (3)

Bill Prin
Bill Prin

Reputation: 2518

I originally suggested a static map of Color enums to classes but chrylis pointed out in the comments it's simpler just to make it a field and pass it to the constructor.

public enum Color {
 RED(Red.class),
 BLUE(Blue.class),
 GREEN(Green.class);

 private Class colorClass;
 public Color(Class classColor)  {
    this.colorClass = classColor;
 }

 public ColorClass getValue() {
     return this.colorClass.newInstance();
 }
}

Upvotes: 1

user3453226
user3453226

Reputation:

See Class.forName(String).

Returns the Class object associated with the class or interface with the given string name.

Do not forget to put the full package name of the target. Then you should declare the Color enum like this.

public enum Color {
    RED("package.Red"),
    BLUE("package.Blue"),
    GREEN("package.Green");
    private final String value;
    private Color(String value) {
        this.value = value;
    }
    public String getValue() {
        return value;
    }
}

You may need a specific instance, not just a Class instance.

try {
    Class clazz = Class.forName(Color.RED.getValue());
    if (clazz.isInstance(Red.class)) {
        Red red = (Red)clazz.cast(Red.class);
    } else if (clazz.isInstance(Blue.class)) {
        Blue blue = (Blue)clazz.cast(Blue.class);
    } else if (clazz.isInstance(Green.class)) {
        Green green = (Green)clazz.cast(Green.class);
    }
} catch (ClassNotFoundException classNotFound) {
    // A class named "package.Red" cannot be found
}

Upvotes: 1

OldCurmudgeon
OldCurmudgeon

Reputation: 65811

You can make the enum a factory.

interface AColour {
};

static class Red implements AColour {

}

static class Green implements AColour {

}

static class Blue implements AColour {

}

enum Colour {

    RED {

                @Override
                AColour makeColour() {
                    return new Red();
                }

            },
    GREEN {

                @Override
                AColour makeColour() {
                    return new Green();
                }

            },
    BLUE {

                @Override
                AColour makeColour() {
                    return new Blue();
                }

            };

    abstract AColour makeColour();
}

class TestClass {

    Colour colour = Colour.RED;

    AColour make() {
        return colour.makeColour();
    }
}

Upvotes: 3

Related Questions