我有Collection<T>
。我有一个类TManager实现了一个接口UManager,它有一个方法getCollection()
,需要返回一个Collection<U>
,其中U是一个接口,T是一个实现U的类。
除了投射它之外,例如return (Collection<U>)Tcoll;
,有更正确的方法来处理这个问题吗?
我在这里控制所有4个类/接口。我将UManager.getCollection
声明为
public Collection<U> getCollection();
应该是
public Collection<? extends U> getCollection()
答案 0 :(得分:3)
这取决于你需要对Collection做什么。如果您不需要在返回的集合中放入任何内容,请使用extends参数
public interface UInterface {
Collection<? extends UInterface> getCollection();
}
完成它。如果将来你确实需要添加到集合中,将它包装在一个新的Collection中并添加all就可以完成这项工作,忽略它的性能(对于编译时问题,额外的运行时性能命中)。
但是,如果目的是返回一个可变集合,那么可以在接口中添加一个类型参数:
public interface UInterface<T extends UInterface> {
Collection<T> getCollection();
}
然后你的实施将是:
public class TClass implements UInterface<TClass> {
pubic Collection<TClass> getCollection();
}
这种方法的问题在于,您必须在运行时使用类型参数来使用接口从中获取可变集合,或者引用具体类。
答案 1 :(得分:2)
应该是:
public Collection<U> getCollection();
尝试avoid bounded wildcards in return types。
子类只会将返回的引用类型声明为Collection<U>
而不是Collection<T>
。这将消除你的演员表。
但是,如果你确实看到需要在返回类型中使用有界通配符,那么我猜你将不得不返回Collection<? extends U>
并且不需要强制转换。
答案 2 :(得分:1)
我相信你想要:
public Collection<? extends U> getCollection();
您可以找到一些关于此here.
的官方文档 @Jason,你是对的。 doc没有明确地调用返回类型,但确实有效。这是一个演示语法的示例方法:public Collection<? extends Throwable> getErrors() {
return new ArrayList<Exception>();
}
答案 3 :(得分:1)
您的topicstart有点令人困惑,因为通用类型通常使用单字符标识符,但您明确提到了接口和类。所以你在寻找这样的东西吗?
interface UManager<T extends UInterface> {
Collection<T> getCollection();
}
class TManager implements UManager<TClass> {
public Collection<TClass> getCollection() {
return Arrays.asList(new TClass(), new TClass());
}
}
interface UInterface {
}
class TClass implements UInterface {
}