Class上未经检查的警告
假设我有以下方法,可用于创建指定给定类型的集合。
private static Collection<?> void create(Class<? extends Collection<?>> cls) {
return cls.newInstance();
}
如果在运行时传入 cls 参数,这一切都很好:
List<String> list = new LinkedList<String>();
create(list.getClass());
但是如何在代码中调用此方法而不出现未经检查的警告?假设我想做类似的事情:
create(LinkedList.class);
它会抱怨 create(Class) 未定义,严格来说这是正确的,因为 List 不是 Collection 的 #capture,但我该如何让它工作呢?
非常感谢!
Suppose I have the following method, which can be used to create a collection of a given type specified.
private static Collection<?> void create(Class<? extends Collection<?>> cls) {
return cls.newInstance();
}
This is all good if the cls argument is passed in during runtime:
List<String> list = new LinkedList<String>();
create(list.getClass());
But how do I invoke this method in code without an unchecked warning? Say I want to do something like:
create(LinkedList.class);
It'll complain that create(Class) is not defined, which strictly speaking is correct because List is not #capture of Collection, but how do I make it work?
Many thanks!
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
Neal Gafter 在此处讨论了这个问题。解决方法是使用超级类型标记。我相信,这就是 Guice 用来维护通用类型信息的方法。
基本上,它是一个额外的类,您可以使用它来表示类型,而不是使用
Foo.class
。您可以这样使用它:请注意,您尝试使用 raw 类型
LinkedList
仍然会导致编译器抱怨,并且是故意的 - 当您使用原始类型时,你基本上选择退出类型安全。但这种方案允许您以一种更困难的方式表达泛型类型。Neal Gafter talks about pretty much exactly this problem here. The fix is to use super type tokens. This is what Guice uses to maintain generic type information, I believe.
Basically it's an extra class you can use to represent a type instead of using
Foo.class
. You'd use it like this:Note that your attempt to use the raw type
LinkedList
would still cause the compiler to complain, and deliberately so - when you use raw types, you're basically opting out of type safety. But this scheme allows you to express the generic type in a way which is otherwise harder.我们这里有两种泛型类型,一种用于集合的子类型,一种用于集合的元素类型。以下代码可以工作:
使用示例。没有警告。
现在的问题是我们如何获得
clazz
?你必须非常努力地说服编译器:我们可以有一个实用方法来简化类型转换:
乐趣是递归的:
但在某些时候,我们必须停止这个愚蠢的游戏。通用类型应该帮助我们,而不是折磨我们。当它变得太麻烦并且使我们的程序无法阅读时,就放弃它吧。使用我们已经快乐地生活了很多年的该死的原始类型。
we have two generic types here, one for subtype of collection, one for element type of collection. following code can work:
usage example. no warnings.
the question now becomes how do we obtain
clazz
? You have to convince the compiler really hard:we can have a utility method to ease the type casting:
The fun is recurive:
But at some point, we have to stop this silly game. Generic typing is supposed to help us, not to torture us. When it becomes too cumbersome and makes our programs impossible to read, just drop it. Use the god damn raw types that we have lived with happily for years.