Java泛型查询(Upper Bounded Wildcards)

时间:2014-09-10 07:32:11

标签: java generics

考虑下面的场景,Class FastCar从Car Class扩展:

public class FastCar extends Car {}

主要方法中的代码段:

Set<? extends Car> mySet6 = null;
mySet6.add(new FastCar()); //<-----compile error  

编译错误详细信息:

(The method add(capture#4-of ? extends Car) in the type Set<capture#4-of ? 
extends Car> is not applicable for )

我很困惑为什么FastCar对象无法放入&#34;对象集合扩展Car&#34;,任何人都可以帮忙澄清?感谢。

2 个答案:

答案 0 :(得分:2)

泛型的目的是提供类型安全操作(并禁止非类型安全操作)。

对于类型为Set<? extends Car>的变量,编译器允许指定类型为Set<SlowCar>的值,因为Set<SlowCar>扩展了Set<? extends Car>。如果您这样做,将FastCar添加到只允许Set的{​​{1}}显然会出错。因此,也不允许将SlowCar添加到允许FastCar的{​​{1}},因为它不是类型安全的。

Set

在您的情况下,应使用? extends Car

Set<SlowCar> slowSet = ...;

slowSet.add(new FastCar()); // Obviously ERROR, FastCar does not extend SlowCar

Set<? extends Car> carSet = slowSet; // Allowed, valid (SlowCar extends Car)

carSet.add(new FastCar());   // Error, because carSet might be
                             // and actually is a set of SlowCars

答案 1 :(得分:1)

这个案例在Java Tutorials about wildcars中得到了很好的解释。我将重新制定它(我重命名了类型和对象名称):

您应该能够弄清楚为什么不允许上面的代码。该 mySet6.add()的参数类型为? extends Car - an 未知的Car子类型。由于我们不知道它是什么类型,我们 不知道它是否是FastCar的超类型;它可能会也可能不会 这样的超类型,因此传递FastCar是不安全的。

http://docs.oracle.com/javase/tutorial/extra/generics/wildcards.html