You don't use type parameters like that. The type parameters can either be declared at Class level or method level. With field declaration like that, you have to use wildcards:
static final Map<String, Class<? extends HasDescription>> CLASSES = new LinkedHashMap<String,Class<? extends HasDescription>>() {{
put( "command1", com.foobar.package_a.ClassOne.class );
put( "command2", com.foobar.package_a.ClassTwo.class );
put( "command3", com.foobar.package_b.ClassThree.class );
}};
I've tried both
implements
andextends
In generics, you just use extends
keyword to represent both the concepts.
Ideally .getDescription() would be static.
No you can't do that. That would not give you polymorphic behaviour that you want currently.
If a pull out a properly qualified class variable, is there a shortcut or special version of reflection that just lets me say something like
( (HasDescription)clazz ).getDescription()
?
If you want to invoke the method like that, then why are you storing the Class
instance instead of the instance itself? If you are storing the Class
instance, you would have to instantiate it using Class#newInstance()
method, and ensure that all the implementating classes provide a 0-arg constructor for that.
Does specifying that all classes must implement a particular interface buy me anything in this usage scenario?
If you're storing the Class
instance, then you have to do that. But if you store the instances themselves, then just keeping the reference as HasDescription
would work fine:
static final Map<String, HasDescription> map = new LinkedHashMap<>();
map.put("command1", new com.foobar.package_a.ClassOne());
map.put("command2", new com.foobar.package_a.ClassTwo());
and then you can do:
map.get("command1").getDescription();