[英]Return a Class instance with its generic type
这是一个简单的示例,演示了我遇到的与类型擦除相关的问题。 我有一个这样的课:
public abstract class AbstractHandler<T> {
...
public abstract Class<T> handledType();
}
然后我有这个实现:
public class ConcreteHandler extends AbstractHandler<Map<String, List<Thing>>> {
@Override
public Class<Map<String, List<Thing>>> handledType() {
//what do I return here?!
}
}
我不能返回Map<String, List<Thing>>.class
,因为它甚至不能在语法上有效。 我尝试将子类型中的泛型类型参数设置为HashMap<String, List<Thing>>
然后返回new HashMap<String, List<Thing>>().getClass()
,但这不起作用,因为返回类型Class<T>#getClass()
是Class<? extends T>
Class<? extends T>
。 我从Guava看了TypeToken
, getRawType
方法看起来很有希望,但它返回Class<? super T>
Class<? super T>
。
我现在有一个解决方法,看起来像这样:
public class ThingListMap {
private Map<String, List<Thing>> thingListMap;
...
}
我只是使用ThingListMap
作为泛型类型参数。
另一种可能的解决方法是执行强制转换:
public Class<Map<String, List<Thing>>> handledType() {
return (Class<Map<String, List<Thing>>>) new HashMap<String, List<Thing>>().getClass();
}
有更优雅的方式吗?
编辑:响应其中一个答案,我无法更改handledType
方法的签名,因为我不拥有或控制其来源。
出于某种原因,Java不允许您将Map.class
直接转换为Class<Map<String, List<Thing>>>
。 无论如何,这是一个未经检查的演员。
但是将它强制转换两次是合法的,首先是Class<?>
,然后是Class<Map<String, List<Thing>>>
。
return (Class<Map<String, List<Thing>>>) (Class<?>) Map.class;
作为未经检查的演员,您可能想要添加@SuppressWarnings("unchecked")
。
Guava的方法是使用TypeToken
。 你的课将成为
public abstract class AbstractHandler<T> {
public TypeToken<T> handledType();
}
public class ConcreteHandler extends AbstractHandler<Map<String, List<Thing>>> {
@Override
public TypeToken<Map<String, List<Thing>>> handledType() {
return new TypeToken<Map<String, List<Thing>>>() {};
}
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.