考虑您有这个列表:
private final List<? extends AbstractXmlElement> inMemoryElements;
包含AbstractXmlElement的子类的一组对象,并且您希望添加一个方法来从该列表中筛选特定子类的对象。为此,我创建了以下方法:
public <E extends AbstractXmlElement> List<E> getInstancesOf(Class<E> c) {
return getUsableElements().stream()
.filter(c::isInstance)
.map(e -> (E) e)
.collect(Collectors.toList());
}
但是(E(E会导致UncheckedCast警告。我想知道这究竟是一个未检查的强制转换,以及是否可以安全地取消此警告,因为那些不是E实例的对象在强制转换之前会被过滤掉。这意味着,据我所知,演员阵容永远不会让失败
这是一个未检查的强制转换,因为E
的类型在运行时是未知的。由于您正在检查isInstance()
,因此您的代码是安全的。但如果你想避免警告,你可以使用c
来进行投射:
.map(c::cast)
这究竟是一个未检查的强制转换
您唯一的保证是e
是AbstractXmlElement
的实例。但它可以是任何子类。因此,如果您有一个子类A
和B
都扩展了AbstractXmlElement
,理论上,类型约束意味着您可以尝试将A
强制转换为B
,如果您将B.class
作为参数传递,并且您的集合包含A
的实例,则会失败。因此发出警告。
请注意,编译器不会去检查你的过滤器表达式,以找出只有E
的实例才能通过过滤器;特别是,它不会去阅读文档,然后还假设文档是正确的。据它所知,c::isInstance()
只是另一种取Object
并返回boolean
的随机方法。在这一点上没有任何内容表明只有CCD_ 17的实例保留在经过过滤器的流中。
如果可以安全地抑制此警告
在这种情况下,是的。