List
界面有两种方法listIterator()
和iterator()
。为什么这两个都是必需的。
来自docs:
Iterator<E> iterator()
Returns an iterator over the elements in this list in proper sequence.
ListIterator<E> listIterator()
Returns a list iterator over the elements in this list (in proper sequence).
ListIterator<E> listIterator(int index)
Returns a list iterator over the elements in this list (in proper sequence), starting at the
specified position in the list. The specified index indicates the first element that would be
returned by an initial call to next. An initial call to previous would return the element with the
specified index minus one.
基本上,ListIterator()
有另外的方法来获取previous and next
元素,而Iterator()
只有next
个元素。这仅用于此目的,还有另一个ListIterator() interface
和listiterator() method in List inteface
答案 0 :(得分:4)
从Java 5开始,可以使用更具体的返回类型(称为协变返回类型)覆盖方法。但是Java 1.2引入了ListIterator
。为了避免使用iterator()
,必须有一种新的方法。
无法从Java 5更改API,因为如果大多数实现返回{{{}},那么List
的所有实现都不会声明iterator()
返回ListIterator
1}}实例中的实例。
类似的困境是ListIterator
和Enumeration
。现在Iterator
会扩展Iterator
,只需添加Enumeration
方法。或者更好的remove()
会替换Iterator
,而Enumeration
会添加ModifiableIterator
。
答案 1 :(得分:2)
具体而言,它们都是必需的,因为List
是一种Iterable
类型,用于指定Iterator iterator()
方法。
现在List
可以简单地覆盖iterator()
中的Iterable
方法,以声明返回类型ListIterator
,其类型为Iterator
(从而满足合同)。为什么没有这样做可能是一个设计决定。
编辑:
@ajb在评论中指出,在创建List
接口后,Java SE 5中添加了协变返回类型。这解释了为什么List
有两种方法,因为{1.2}返回类型在Java 1.2中无法缩小为iterator()
。
答案 2 :(得分:1)
Java的设计非常坚固 - 允许大量的语言实现更改,这些更改不会影响在java上运行的代码。
例如,您通常可以将“Java JRE 6”替换为“Java JRE 7”而不会出现大多数代码的问题 - 这是使用新语法进行的整个语言升级。您还可以使用开源实现替换Java JRE,您将获得相同的结果 - 这些东西几乎可以正常工作。
因此,当他们设计一个类时,他们必须为实现者和编码器设计它。
如果他们只是让一个ArrayList为“Iterable”,那么对于ArrayLists,返回一个ListIterator类型的Iterator,然后接口不需要另一个实现者(OpenJDK)来返回正确的类型 - 不仅如此,而是用户在没有查看文档的情况下不知道返回了什么类型(如果每个人都按这种方式编程,那么Eclipse ctrl-space就不那么有用了。)
Java通常会尝试尽可能明确地表达......这是一件非常好的事情,因为它会停止猜测和相关错误。
当不可能使接口和类型足够明确时,他们对其文档非常谨慎,但如果可能的话,他们会避免这种情况。
答案 3 :(得分:0)
似乎Iterator将用于单链表,ListIterator用于双向链表。