迭代器
如果从更高层的角度思考,会发现这里有个缺点:要使用容器,必须对容器的确切类型编程。初看起来这没什么不好,但考虑下面情况,如果原版对List编码的,但是后来发现如果能够把相同的代码用于Set,将会非常方便,应该怎么做?
这里就要使用迭代器,迭代器是一个对象,它的工作是遍历并选择序列中的对象,而不必关心底层架构。
java中的Iterator只能单向移动,而且这个Iterator只能用来:
- 使用方法Iterator()要求容器返回一个Iterator。Iterator将准备好返回序列的第一个元素。
- 使用next()获得序列中的下一个元素。
- 使用hasNext()检测序列中是否还有元素。
- 使用remove()将迭代器新近返回的元素删除。
下面用一个例子,顺便把前面的知识也串一下:
public class TestIterator {
public class Word{
int id;
String name;
Word(int i,String n){id=i;name=n;}
}
public static void display(Iterator<Word> it){
while(it.hasNext()){
Word w = it.next();
System.out.println("name:"+w.id+", id:"+w.name);
}
}
public static void main(String[] args) {
// TODO Auto-generated method stub
TestIterator ti = new TestIterator();
List<Word> l = new LinkedList<Word>();
l.addAll(Arrays.asList(ti.new Word(0,"A"),ti.new Word(1,"B")));
display(l.iterator());
Set<Word> s = new HashSet<>();
s.addAll(Arrays.asList(ti.new Word(2,"C"),ti.new Word(3,"D")));
display(s.iterator());
}
}
Collection
Collection是描述所有序列容器的共性的根接口,我们可以通过针对接口而非具体实现来编写代码。
可以直接在上面的代码加上使用Collection的方法:
public class TestIterator {
public class Word{
int id;
String name;
Word(int i,String n){id=i;name=n;}
}
public static void display(Iterator<Word> it){
while(it.hasNext()){
Word w = it.next();
System.out.println("Iterator: name:"+w.id+", id:"+w.name);
}
}
public static void display(Collection<Word> c){
for(Word w:c){
System.out.println("Collection: name:"+w.id+", id:"+w.name);
}
}
public static void main(String[] args) {
// TODO Auto-generated method stub
TestIterator ti = new TestIterator();
List<Word> l = new LinkedList<Word>();
l.addAll(Arrays.asList(ti.new Word(0,"A"),ti.new Word(1,"B")));
Set<Word> s = new HashSet<>();
s.addAll(Arrays.asList(ti.new Word(2,"C"),ti.new Word(3,"D")));
display(l.iterator());
display(s.iterator());
display(s);
display(l);
}
}
输出:
Iterator: name:0, id:A
Iterator: name:1, id:B
Iterator: name:2, id:C
Iterator: name:3, id:D
Collection: name:2, id:C
Collection: name:3, id:D
Collection: name:0, id:A
Collection: name:1, id:B
对于当前例子来说,两种方法都可以,但是,当你要实现一个不是Collection的外部类时,由于让它去实现Collection的接口可能非常困难或麻烦。