簡介
Provide a way to access the elements of an aggregate object sequentially without exposing its underlying representation.
提供一種順序訪問聚集/容器對(duì)象元素的方法,而又無須暴露聚集內(nèi)部表象。
迭代器模式(Iterator Pattern) 又稱為 游標(biāo)(Cursor)模式,是對(duì)象的行為模式。
迭代器模式 可以順序地訪問一個(gè)聚集中的元素,而又不會(huì)暴露聚集內(nèi)部表象。也即 迭代器模式 可以為不同的容器提供一致的遍歷行為,而不用關(guān)心容器內(nèi)容元素組成結(jié)構(gòu)。
迭代器模式 本質(zhì):抽離聚集對(duì)象迭代行為到迭代器中,提供一致訪問接口。
主要解決
我們把多個(gè)對(duì)象聚在一起形成的總體稱之為聚集(Aggregate),聚集對(duì)象是能夠包容一組對(duì)象的容器對(duì)象。不同的聚集其內(nèi)部元素的聚合結(jié)構(gòu)可能不同,而 迭代器模式 屏蔽了內(nèi)部元素獲取細(xì)節(jié),為外部提供一致的元素訪問行為,解耦了元素迭代與集合對(duì)象間的耦合,并且通過提供不同的迭代器,可以為同個(gè)聚集對(duì)象提供不同順序的元素訪問行為,擴(kuò)展了聚集對(duì)象元素迭代功能,符合 開閉原則。
優(yōu)缺點(diǎn)
優(yōu)點(diǎn)
- 多態(tài)迭代:為不同的聚合結(jié)構(gòu)提供一致的遍歷接口,即一個(gè)迭代接口可以訪問不同的聚集對(duì)象;
- 簡化聚集對(duì)象接口:迭代器模式 將聚集對(duì)象本身應(yīng)該提供的元素迭代接口抽取到了迭代器中,使聚集對(duì)象無須關(guān)心具體迭代行為;
- 元素迭代功能多樣化:每個(gè)聚集對(duì)象都可以提供一個(gè)或多個(gè)不同的迭代器,使的同種元素聚合結(jié)構(gòu)可以有不同的迭代行為;
- 解耦迭代與聚集:迭代器模式 封裝了具體的迭代算法,迭代算法的變化,不會(huì)影響到聚集對(duì)象的架構(gòu);
缺點(diǎn)
- 對(duì)于比較簡單的遍歷(像數(shù)組或者有序列表),使用迭代器方式遍歷較為繁瑣;
使用場(chǎng)景
- 遍歷一個(gè)容器對(duì)象時(shí);
模式講解
首先來看下 迭代器模式 的通用 UML 類圖:

從 UML 類圖中,我們可以看到,迭代器模式 主要包含三種角色:
- 抽象迭代器(Iterator):抽象迭代器負(fù)責(zé)定義訪問和遍歷元素的接口;
- 具體迭代器(ConcreteIterator):提供具體的元素遍歷行為;
- 抽象容器(Aggregate):負(fù)責(zé)定義提供具體迭代器的接口;
- 具體容器(ConcreteAggregate):創(chuàng)建具體迭代器;
以下是 迭代器模式 的通用代碼:
class Client {
public static void main(String[] args) {
//來一個(gè)容器對(duì)象
IAggregate<String> aggregate = new ConcreteAggregate<>();
//添加元素
aggregate.add("one");
aggregate.add("two");
aggregate.add("three");
//獲取容器對(duì)象迭代器
Iterator<String> iterator = aggregate.iterator();
//遍歷
while (iterator.hasNext()) {
String element = iterator.next();
System.out.println(element);
}
}
//抽象迭代器
interface Iterator<E> {
E next();
boolean hasNext();
}
//具體迭代器
static class ConcreteIterator<E> implements Iterator<E> {
private List<E> mList;
private int mCursor = 0;
public ConcreteIterator(List<E> list) {
this.mList = list;
}
@Override
public E next() {
return this.mList.get(this.mCursor++);
}
@Override
public boolean hasNext() {
return this.mCursor < this.mList.size();
}
}
//抽象容器
interface IAggregate<E> {
boolean add(E element);
boolean remove(E element);
Iterator<E> iterator();
}
//具體容器
static class ConcreteAggregate<E> implements IAggregate<E> {
private List<E> mList = new ArrayList<>();
@Override
public boolean add(E element) {
return this.mList.add(element);
}
@Override
public boolean remove(E element) {
return this.mList.remove(element);
}
@Override
public Iterator<E> iterator() {
return new ConcreteIterator<E>(this.mList);
}
}
}
通過上面的代碼,我們可以更清楚地了解到 迭代器模式 的作用就是將聚集對(duì)象的迭代行為抽取到迭代器中,解耦了元素迭代與聚集對(duì)象之間的耦合,使得不同的聚集對(duì)象對(duì)外都能提供一致的迭代行為。
注:認(rèn)真思考一下 迭代器模式 和 組合模式,其實(shí)這兩者似乎存在一定的相似性。組合模式 解決的是統(tǒng)一樹形結(jié)構(gòu)各層次訪問接口,迭代器模式 解決的是統(tǒng)一各聚集對(duì)象元素遍歷接口。雖然他們的適配場(chǎng)景不同,但核心理念是相通的。