Java Collection | Set 0 (Iterator)

Java Collection 即 Java 的集合框架,何为集合框架,Wikipedia 上是这么解释的:

The Java collections framework (JCF) is a set of classes and interfaces that implement commonly reusable collection data structures.

Although referred to as a framework, it works in a manner of a library. The JCF provides both interfaces that define various collections and classes that implement them.

由此可知,Java Collection 集成了常用的数据结构,提供了接口和实现。

那么接口和接口之间的关系是怎样的呢?哪一个类又实现了哪一个接口呢?

下面这张图很好的表现出了它们之间的关系:

Java Collection Framework

Image Source : https://www.ntu.edu.sg/home/ehchua/programming/java/J5c_Collection.html

我们前几天讨论的 LinkedList 即为 List 接口的实现类之一。

不同的实现类具有不同的功能,下面来一一讨论:

Iterator 接口

Iterator 即为“迭代器”,用于一个一个取出容器里的元素。在 Java 中,Iterator 分为以下三种:

Enumeration**

可以使用 elements()方法来创建一个 Enumeration 对象
Enumeration 接口中提供了两种方法:
public boolean hasMoreElements();用于判断是否还有下一个对象
public Object nextElement();用于返回下一个对象

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
import java.util.Enumeration;
import java.util.Vector;
public class EnumerationDemo{
public static void main(String[] args){
Vector v = new Vector();
for (int i = 0; i < 10; i++){
v.addElement(i);
}
System.out.println(v);
Enumeration e = v.elements();
while (e.hasMoreElements()){
int i = (Integer)e.nextElement();
System.out.print(i + " ");
}
System.out.println();
}
}

Source: http://www.geeksforgeeks.org/iterators-in-java/

Enumeration 的局限性在于

它是JDK 1.0添加的接口,使用到它的函数只包括Vector、Hashtable等类。这些类都是JDK 1.0中加入的,Enumeration存在的目的就是为它们提供遍历接口。不具普遍性。

它只能从头到尾遍历,只能读取数据,不能移除,也无法改动。

Iterator

Iterator 是JDK 1.2才添加的接口,它可以为任何集合对象提供遍历接口。它比 Enumeration 更有通用性。

可以用iterator()方法来构造一个 Iterator 对象: Iterator itr = c.iterator();

Iterator 接口定义了三种方法:
public boolean hasNext(); // Returns true if the iteration has more elements
public Object next(); // Returns the next element in the iteration
public void remove(); // Remove the next element in the iteration

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
import java.util.Iterator;
import java.util.Vector;
public class EnumerationDemo{
public static void main(String[] args){
Vector v = new Vector();
for (int i = 0; i < 10; i++){
v.addElement(i);
}
System.out.println(v);
Iterator itr = v.iterator();
while (itr.hasNext()){
int i = (Integer) itr.next();
System.out.print(i + " ");
if (i % 2 == 0) itr.remove();
}
System.out.println();
System.out.println(v);
}
}

Iterator 的局限性:只能从左到右遍历。无法替换或增加新的元素。

ListIterator

需要注意的是,ListIterator 只对 List 接口的实现类有效,如 ArrayList,LinkedList。它比 Iterator 拥有更多的方法

可以使用 listIterator()方法构造一个ListIterator对象
ListIterator ltr = l.listIterator() // l refers any list object

ListIterator 具有的方法如下:
这三个方法继承了 Iterator,与 Iterator 的方法具有相同的功能:
hasNext(), next(), remove()
hasPrevious(), previous()hasNext(), next() 正好相反
nextIndex(), previousIndex() 分别返回下一个和上一个对象的索引

另外两个方法:
// Replaces the last element returned by next() or previous() with the specified element
public void set(Object obj);

// Inserts the specified element into the list at position,
// before the element that would be returned by next()
public void add(Object obj);

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
import java.util.ListIterator;
import java.util.Vector;
public class EnumerationDemo{
public static void main(String[] args){
Vector v = new Vector();
for (int i = 0; i < 10; i++){
v.addElement(i);
}
System.out.println(v);
ListIterator ltr = v.listIterator();
while (ltr.hasNext()){
int i = (Integer) ltr.next();
System.out.print(i + " ");
if (i % 2 == 0){
i++;
ltr.set(i);
ltr.add(i);
}
}
System.out.println();
System.out.println(v);
}
}

Source: http://www.geeksforgeeks.org/iterators-in-java/
运行结果

[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
0 1 2 3 4 5 6 7 8 9
[1, 1, 1, 3, 3, 3, 5, 5, 5, 7, 7, 7, 9, 9, 9]

Iterator 与 Foreach 的比较

Iterating over collection ‘c’ using Iterator

1
2
3
for (Iterator i = c.iterator(); i.hasNext(); ){
System.out.println(i.next());
}

Iterating over collection ‘c’ using Foreach

1
2
3
for (Element e : c){
System.out.println(e);
}

在 Java8 中,使用 Lambda 表达式,还可以把 Foreach 写成这样

1
elements.forEach (e -> System.out.println(e) );

Foreach 只能遍历元素,无法修改。
要想修改元素,只能使用 Iterator。

Reference:

  1. Geeksforgeeks
  2. Wikipedia
谢谢你请我吃糖果:)