2013-09-21 161 views
4

这两个List s有区别吗?List <Something>和List <?有什么区别?扩展Something>?

List<Something> a; 
List<? extends Something> b; 

我知道,例如

List<Object> a; 
List<?> b; 
List c; 

List<Something> a; 
List<? extends SomeInterfaceSomethingImplements> b; 

都是不同的,但这些怎么样?如果Something被替换为Object,它会不同吗?

List<Object> a; 
List<? extends Object> b; 
+0

请参阅:http://stackoverflow.com/questions/897935/when-do-java-generics-require-extends-t-instead-of-t-and-is-there-any-down –

+0

Makind类型一个字段'列表'只允许你为它分配一个'List '。由于类型擦除,“列表”不被视为“列表”。声明为List <的引用? extends Object>'可以被赋予一个属于Object的任意子类的元素列表(对Java中的所有类都适用)。这可能意味着'清单','清单','清单' – toniedzwiedz

+0

@Tom对,除了我很确定这不是因为类型擦除。 'String'和'Object'已经存在,它们只是被检查,它与擦除类型无关。 – Dukeling

回答

8

List<Something>Something类型的对象的列表。 List<? extends Something>是延伸Something的某些特定类型的对象的列表。

因此,List<Object>可以有任何类别的对象,延伸Object。 但List<? extends Object>只能被初始化为或指定为特定类的对象的列表,其可以延伸Object

这是有用的吗?假设你要编写需要的Objects一个List并打印每个项目的方法:

void print(List<Object> list) { 
    for (Object obj: list) { 
     System.out.println(obj) 
    } 
} 

现在,让我们说你有一个List<Integer>。您无法将它传递给上述方法,因为print需要List<Object>,并且List<Integer>不能分配给List<Object>。为了解决这个问题,我们重新定义print为:

void print2(List<? extends Object> list) { 
    for (Object obj: list) { 
     System.out.println(obj) 
    } 
} 

现在,我们可以通过列出对象的任何子类的来print2print2将接受List<Integer>List<String>

在另一面,你不能在列表中添加任何东西里面print2,因为print2不知道所使用的Object的具体亚型。因此,您只能在不需要向List添加任何内容的方法中使用? extends ...

+0

'List <?扩展Object>'也可以初始化为'List '。 – Ryan

+0

@瑞恩,是的,它可以。 '?'的用处在于它也可以分配给'List ',而您不能将'List '分配给'List ' –

+0

为什么选择down-vote? –

1

List<Something>表示执行应该是类似于ArrayList<Something>。但另一种情况List<? extends Something>意味着实现可以是任何类似于ArrayList<Something>ArrayList<SomethingChild>其中SomethingChild延伸Something

您可以指定

List<? extends Something> list = new ArrayList<SomethingChild>(); 

,而不能分配

List<Something> list = new ArrayList<SomethingChild>(); 

这将导致编译错误。

您可以了解更多关于泛型用于获取一些真知灼见

2

正如其他人所说泛型和通配符,List<Something>Something类型的对象的列表,而List<? extends Something>将被初始化为不同的列表对象类型,只要对象类型延伸Something

List<Object>将是Object类型的对象列表。

List<? extends Object>可能被初始化为扩展为Object的任何数据类型的列表。

这里是在使用Object相比? extends Object时会发生什么一些代码:

import java.util.ArrayList; 

public class test { 
    class A {} 

    public static void main(String[] args) { 
     // No error 
     ArrayList<Object> arrObj = new ArrayList<Object>(); 

     // Error 
     ArrayList<Object> arrObj2 = new ArrayList<A>(); 

     // No Error 
     ArrayList<? extends Object> arrExt = new ArrayList<Object>(); 

     // No Error 
     ArrayList<? extends Object> arrExt2 = new ArrayList<A>(); 
    } 

} 
0

首先就是对象类型收集的东西,第二个是,是某种亚型对象的集合。

相关问题