我有一个关于 Java泛型的基本问题。我认为List<Number>
和List<? extends Number>
都是同质的。我是对的还是有一些我缺少的基础?
答案 0 :(得分:7)
通用类型更迂腐。
<? extends Number>
表示Number或未知的子类。如果您获得这样的值,它将是Number
,但您不能给出此类型的值,因为您不知道哪个有效。
区别在于参数和返回值。
List<Number> numbers = new ArrayList<Number>();
Number n = 1;
numbers.add(n); // ok.
n = numbers.get(0); // ok
numbers.add(1); // ok.
List<? extends Number> numbers2 = new ArrayList<Double>();
numbers2.add(n); // not ok
n = numbers2.get(0); // ok
List<? super Number> numbers3 = new ArrayList<Serializable>();
numbers3.add(n); // ok
n = numbers3.get(0); // not ok.
super
来表示类型可以是超类型。 e.g。
在集合中,此方法表示比较器需要能够比较相同类型或任何超类型。
public static <T> void sort(List<T> list, Comparator<? super T> c)
这意味着你可以拥有
Comparator<Number> comparesAnyNumbers = ...
List<Integer> ints = ...
Collections.sort(ints, comparesAnyNumbers);
答案 1 :(得分:2)
泛型是编译时语言的特性,意味着它们在运行时不存在。 在通用机制中,对于编译时检查,它们不是同类的,即如果要在泛型类型中使用多态。
以下给出了编译时错误,尽管它似乎是一个有效的定义:
List<Number> list = new ArrayList <Integer>();
而
List<? extends Number> list = new ArrayList <Integer>();
有效。此外,您不能在右侧使用通配符类型:
List list = new ArrayList <? extends Integer>();
不会被编译。
答案 2 :(得分:1)
List<Number>
- &gt; Number
的列表(或Number
的实例)
List<? extends Number>
- &gt;列出任何扩展Number