Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

HashMap<Class<?>, List<Class<?>>> : specify that the lists' classes extend the keys'

One of my class need to store classes according to their superclasses. To that end, I'm using a HashMap, where keys are the superclasses, and values a list of their extended classes. So it looks like that :

HashMap<Class<?>, List<Class<?>>>

I'd like to know if there was a notation allowing me to be more precise, something like :

HashMap<Class<T>, List<Class<? extends T>>>

I've tried that and, of course, it doesn't work : T cannot be resolved. Is there a syntax that would allow me to do that ? Thanks in advance for your help.

like image 961
Raveline Avatar asked Nov 18 '11 14:11

Raveline


People also ask

How do you make a class a key in a HashMap?

We can conclude that to use a custom class for a key, it is necessary that hashCode() and equals() are implemented correctly. To put it simply, we have to ensure that the hashCode() method returns: the same value for the object as long as the state doesn't change (Internal Consistency)

How hashCode () and equals () method are used in HashMap?

In HashMap, hashCode() is used to calculate the bucket and therefore calculate the index. equals() method: This method is used to check whether 2 objects are equal or not. This method is provided by the Object class. You can override this in your class to provide your implementation.

How do you make an employee object a key in HashMap?

If you want to make a mutable object as a key in the hashmap, then you have to make sure that the state change for the key object does not change the hashcode of the object. This can be done by overriding the hashCode() method. But, you must make sure you are honoring the contract with equals() also.

What is the requirement for an object to be used as key or value in HashMap?

Question: What is the requirement for using Object as a key or value in HashMap? In HashMap, the key or value object must implement the equals() and hashcode() method.


2 Answers

You can do that with accessor methods.

// only accessed by methods which check the keys and values are the right type.
final Map<Class, List<Class>> map = new LinkedHashMap<Class, List<Class>>();

public <T, S extends T> void add(Class<T> key, Class<S> value) {
    List<Class> list = map.get(key);
    if (list == null)
        map.put(key, list = new ArrayList<Class>());
    list.add(value);
}

public <T, S extends T> List<Class<S>>get(Class<T> key) {
    return (List<Class<S>>) map.get(key);
}

public <T, S extends T> boolean contains(Class<T> key, Class<S> value) {
    List<Class> list = map.get(key);
    if (list == null) return false;
    return list.contains(value);
}

public static void main(String... args) {
    Main m = new Main();
    m.add(Number.class, Integer.class); // compiles
    m.add(Number.class, String.class); // does not compile.
}
like image 149
Peter Lawrey Avatar answered Nov 06 '22 20:11

Peter Lawrey


Something like:

class MyMap<T extends Class<?>> extends HashMap<T, List<T>> {

}

Won't entirely solve your problem. You can see that on single entries in the map it cannot vary.

like image 43
Joop Eggen Avatar answered Nov 06 '22 18:11

Joop Eggen