我有点困惑。
我有一个类,它不是集合,但确实引用了通用对象:
public class XClass<E extends AnInterface>{
E instanceobject;
public void add(E toAdd){}
}
public interface AnInterface{}
public class A implements AnInterface{}
public class B implements AnInterface{}
我相信我读过某处(如果声明XClass实例时)要使用
<? extends AnInterface>
(如果您想同时在通用对象中使用多个子类型,而<T extends AnInterface>
仅允许您在该对象中使用一种子类型)。一次通用类?但是,我只能使用:
XClass<AnInterface> xc = new XClass<AnInterface>();
A a = new A();
B b = new B();
xc.add(a);
xc.add(b);
这样,我可以将Supertype的多个子类型传递给泛型类……
我看不到使用“?”的目的使用接口作为通用参数有什么问题吗?
最佳答案
之所以可以同时添加A
和B
类型的对象,是因为您使用接口对XClass进行了参数化,因此添加两个实现该接口的不同类没有错。
另一方面,如果您将XClass定义为:
XClass<A> xc = new XClass<A>();
那么表达式
xc.add(b);
将给出编译错误,因为所有添加的对象必须具有与声明的类型相同的类型,在这种情况下为A。例如,如果您声明
xc
为:XClass<? extends AnInterface> xc = new XClass<AnInterface>();
然后添加
a
或b
不再合法,因为我们所知道的唯一是xc是AnInterface
的某些未知但已修复的子类型,并且无法知道该未知类型是A
还是B
或其他。但是,假设您正在编写一种接受XClass类型的方法,可以对以前添加的元素进行迭代。您唯一的限制(出于示例考虑)是项目扩展了
AnInterface
,您不在乎实际的类型是什么。您可以像下面这样声明此方法:
public static void dummyMethod(XClass<? extends AnInterface> dummy){
//do stuff here, all the elements extend (implement in this case), AnInterface, go wild.
}
现在,您可以将诸如
XClass<A>
,XClass<B>
或XClass<AnInterface>
之类的任何内容传递给此方法,它们都将是有效的。请记住,由于上述相同的原因,您无法将其添加到传递的对象中。我们不知道未知类型是什么!
public static void dummyMethod(XClass<? extends AnInterface> dummy){
//do stuff here, all the elements extend (implement in this case), AnInterface, go wild.
dummy.add(new A()); //you can't do this, we have no idea what type ? stand for in this case
}