2011-08-17 109 views
2

为什么这个不行...实现和集合

public ArrayList<Edge> getEdges() { 

return A; 

//A is an Arraylist of type 'Action'. Action implements Edge. 

} 

接口边缘包括:公共的ArrayList getEdges();

即使这样做。

public Edge getEdges() { 

return B; 

//B is an 'Action'. Action implements Edge. 

} 

界面边缘包括:公共边缘getEdges();

谢谢你, 切特

回答

7

因为尽管EdgeAction一个亚型,ArrayList<Action>不是ArrayList<Edge>一个亚型。

改为使用ArrayList<? extends Edge>

你可以看看this tutorial's 4. Wildcard section,虽然我建议只是仔细阅读它,因为它确实有帮助。

0

因为泛型类型必须相同,不是从它扩展你可以重写这样,它的工作:

public ArrayList<? extends Edge> getEdges() { 

return A; 

//A is an Arraylist of type 'Action'. Action implements Edge. 

} 
2

这是因为ArrayList<E>不是covariant上键入E。也就是说,您不能仅仅因为Derived继承自Base而将ArrayList<Derived>的实例替换为ArrayList<Base>

考虑这种情况:String继承自Object; 然而,如果这意味着你可以使用一个ArrayList<String>作为ArrayList<Object>然后将下面的代码将是可能的:

ArrayList<Object> list = new ArrayList<String>(); 
list.add(new Integer(5)); // Integer inherits from Object 

以上不能正常工作,因为你不能添加IntegerArrayList<String>。如果可以,那么这可能会发生:

ArrayList<String> stringList = (ArrayList<String>)list; 
String string = stringList.get(0); // Not a string! 

至于Ziyao has indicated,实现这个正确的方法是使用? extends Edge语法。

2

香蕉水果。香蕉列表不是水果列表。

Oherwise有人可以构建一个香蕉列表,传递给你一个水果列表的引用,并且你会(正确地)在其中插入一个苹果。香蕉名单的所有者会感到惊讶。

+1

[我是香蕉](http://www.youtube.com/watch?v=LH5ay10RTGY&ob=av3e) – mre