List 无法转换为ArrayList
在我的代码的开头,有:
List<List> result = new ArrayList();
然后,(这是反转子列表):
List sub = new ArrayList(); re = reverse(result.get(j)); // error occurs here
有这种方法:
public ArrayList reverse(ArrayList list) { List newList = new ArrayList(); for(int i=list.size()-1; i>=0; i--) { newList.add(list.get(i));} return newList; } }
错误消息是:
List无法转换为ArrayList
为什么?
想想这样,你有一个名为re
的Fruit
(我使用这个名字,因为它是你正在使用的变量的名称)。
Fruit re;
你有一个方法reverse
其输入类型是Apple
。
public Apple reverse(Apple a) { // ... }
我们有一个变量re
我们宣称为Fruit
,这意味着我们说它总是会成为某种Fruit
,也许是Apple
,但也许是Orange
– 甚至是Banana
。
当你尝试将Fruit
用于采用Apple
的方法时,编译器会阻止你,因为它无法确定它是100%的Apple
。 例如…
Fruit re = new Orange(); reverse(re);
哎呀! 我们正在将一个方形钉子放入圆孔中。 reverse
需要Apple
,而不是Orange
。 坏事可能发生!
旁注:为什么将
Apple
分配给宣称为Fruit
东西呢? (reverse
返回Apple
,Fruit f = reverse(re);
合法。)因为Apple
是Fruit
。 如果它被宣布为更具体的Apple
并且返回类型是更普遍的Fruit
, 那么这里就会出现问题。 (如果reverse
返回Fruit
,Apple a = reverse(re);
将是非法的。)
如果你没有按照这个比喻,将Fruit
替换为List
,将Apple
替换为ArrayList
,再次阅读上述内容。 List
是Fruit
,一种描述抽象概念的一般方式。 ArrayList
是Apple
,是抽象概念的具体实现。 ( LinkedList
也可能是Orange
。)
通常,您希望将事物声明为获得所需function的最常用的东西。 进行以下更改应该可以解决您的问题。
public List reverse(List list) {
我们正在使用某种List
of Integer
并返回某种List
of Integer
s。
您正在使用List
接口的特定实现作为reverse
函数的返回类型(即ArrayList
)。 这会强制您返回的是ArrayList
,但您将其定义为List
。
要理解,请尝试更改构造部件以使用LinkedList
,它也实现List
:
List newList = new LinkedList ();
这种结构是有效的,但现在我们尝试从返回ArrayList
的函数返回一个LinkedList
。 这没有任何意义,因为它们没有关系(但请注意:它们都实现了List
)。
所以现在你有两个选择:
通过强制使用ArrayList
使实现更具体:
ArrayList newList = new ArrayList<>();
或者更好 ,通过更改函数的返回类型(可以插入任何List
)使实现更通用:
public List reverse(List list){
这是因为你的结果varible有一个List类型,但你的方法需要一个ArrayList试试看:
List result = new ArrayList<>();
或改变你的function:
public List reverse(List list){...