Generics and inheritance: need a complex Map instance

て烟熏妆下的殇ゞ 提交于 2020-01-09 07:58:07

问题


public abstract class Mother {
}

public class Daughter extends Mother {
}

public class Son extends Mother {
}

I need a Map which keys are one of Daughter or Son classes, and which values are lists of objects of one of those two classes, respectively.

For example:

/* 1. */ map.put(Daughter.class, new ArrayList<Daughter>()); // should compile
/* 2. */ map.put(Son.class, new ArrayList<Son>()); // should compile
/* 3. */ map.put(Daughter.class, new ArrayList<Son>()); // should not compile
/* 4. */ map.put(Son.class, new ArrayList<Daughter>()); // should not compile

I tried Map<Class<T extends Mother>, List<T>>, but it does not compile.

Map<Class<? extends Mother>, List<? extends Mother>> does compile, but the cases 3. and 4. do compile too while then shouldn't.

Is it even possible?


回答1:


I don't think it's possible to encode this in the type, I'd do it with a custom class

class ClassMap<T> {
  private Map<Class<? extends T>, List<? extends T>> backingMap = new HashMap<>();

  public <E extends T> void put(Class<E> cls, List<E> value) {
    backingMap.put(cls, value);
  }

  @SuppressWarnings("unchecked")
  public <E extends T> List<E> get(Class<E> cls) {
    return (List<E>)backingMap.get(cls);
  }
}

It's safe to suppress warnings here as long as you don't leak the backingMap reference outside this class.




回答2:


Assuming you're looking for a single map, no this is not possible.



来源:https://stackoverflow.com/questions/13845468/generics-and-inheritance-need-a-complex-map-instance

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!