1、模式定义
, ?2 U6 @6 J- \; `0 d7 F: Z迭代器模式(Iterator Pattern) :提供一种方法来访问聚合对象,而不用暴露这个对象的内部表示,其别名为游标(Cursor)。迭代器模式是一种对象行为型模式。6 S; @& M8 t) Z- p
& I& D) _8 D8 Z1 K( |1 V: ^8 ^1 s; A, g2、模式结构5 M& _6 m# ?! \- ]+ e
迭代器模式包含如下角色:
& p- \& H9 R6 _3 i+ f& n3 ZIterator: 抽象迭代器/ C1 C% J7 Z4 D+ c) D/ T2 E! K
ConcreteIterator: 具体迭代器! m! U. P+ G* Q8 `5 {9 K& v7 `% d+ r
Aggregate: 抽象聚合类1 {% X1 a! U+ C0 l
ConcreteAggregate: 具体聚合类
& M7 b% E3 x& d }* @5 ?3、模式分析
- n% r4 N" C7 C- ~% l) h) D聚合是一个管理和组织数据对象的数据结构。" S5 {: D8 D: {
聚合对象主要拥有两个职责:一是存储内部数据;二是遍历内部数据。
0 l' Y. C. C0 A( q r4 C0 p存储数据是聚合对象最基本的职责。
+ b* i( X* _. ]6 T6 m) Z8 j将遍历聚合对象中数据的行为提取出来,封装到一个迭代器中,通过专门的迭代器来遍历聚合对象的内部数据,这就是迭代器模式的本质。迭代器模式是“单一职责原则”的完美体现。% K: {& u' u) Z4 l# V, @
3 W6 V1 ? ?9 H; H2 L; {. ]- D
模式分析# J( a! C# Q% k6 e
自定义迭代器
0 c' X4 `$ L7 x8 o1 O3 DMyIterator——抽象迭代器
+ K, l7 X4 M$ J0 HMyCollection——抽象聚合类/ i( B" [% p- |6 P: w. m
NewCollection——具体聚合类
) ~1 V* g d3 b0 [NewIterator——具体迭代器: o/ Z; B+ K) D
Client X4 Q' l2 O1 G
- public class ConcreteIterator implements Iterator
8 h9 T) ^( v: W h; A - {$ R% c/ Q. r- T* j
- private ConcreteAggregate objects;) E3 ?$ E4 O- U! b5 M; c5 M4 G
- 7 t; ?. p5 T/ c
- public ConcreteIterator(ConcreteAggregate objects)8 Z1 d: U$ I, n! S1 j2 b
- {
: I% Y. A \2 a1 V& P - this.objects=objects;
6 w. j5 ]0 ^, y7 [ - }4 L4 i7 y& D+ s1 j3 v" y& u3 n
- public void first()
1 V2 N) `$ A6 n# J9 `' l& S - { ...... }
& |7 D- X. A" o' a/ f1 \$ f3 Q - 8 J; w/ h1 K+ T% G* g) R
- public void next()
* `. ~& U# }2 n \4 F. w* D - { ...... }" I% J: q$ O2 @* [+ N
- public boolean hasNext()
/ K( w5 I6 G, t/ O3 u8 J - { ...... }" `3 f1 |8 F* |7 f, T$ E4 ^6 _. R! ?
-
6 q$ A2 r" [/ z$ d6 y; F: _# t2 K - public Object currentItem()/ w+ t" U, ~4 v8 f# _, i% f! s
- { ...... }) r" M" H- C5 s% U5 y
- }
5 c v; w% T4 o* ]% \1 r - public class ConcreteAggregate implements Aggregate
% d9 Q A: r! _6 \$ M/ U; Q - {
8 C% q. D2 y; @3 [% O - ......
8 h1 H! n) {" ~2 U$ \ - public Iterator createIterator()2 M( D; W3 @7 Y) t
- {$ B `' ?2 c0 b9 b
- return new ConcreteIterator(this);
$ ~; F% C2 l2 p! v c- x- d, g - }
8 g z- d9 w) r6 c& m9 G6 G - ....../ ]$ U8 H0 ]7 s2 M7 v, A
- }: W |: [8 E( j# L/ k
复制代码 在迭代器模式中应用了工厂方法模式,聚合类充当工厂类,而迭代器充当产品类,由于定义了抽象层,系统的扩展性很好,在客户端可以针对抽象聚合类和抽象迭代器进行编程。0 k% k/ M- A0 o% ]' n9 v" ^
由于很多编程语言的类库都已经实现了迭代器模式,因此在实际使用中我们很少自定义迭代器,只需要直接使用Java、C#等语言中已定义好的迭代器即可,迭代器已经成为我们操作聚合对象的基本工具之一。$ B) Y" J6 }1 w! w% E' j
( [ W3 m* v' H; j8 ~) T
4、模式优缺点1 N4 o G9 `, ^+ G) E0 L1 a
迭代器模式的优点& O. S: K' U( M* h9 m1 w9 V- v
它支持以不同的方式遍历一个聚合对象。9 o% m5 l8 m" {8 @6 B; H2 O% d
迭代器简化了聚合类。
, e# X6 h9 a- i! S2 }7 |- ?在同一个聚合上可以有多个遍历。
7 b2 M2 {1 {# U6 n& \9 d; a9 @在迭代器模式中,增加新的聚合类和迭代器类都很方便,无须修改原有代码,满足“开闭原则”的要求。 迭代器模式的缺点) p5 b/ \# a. j6 {, f! g
由于迭代器模式将存储数据和遍历数据的职责分离,增加新的聚合类需要对应增加新的迭代器类,类的个数成对增加,这在一定程度上增加了系统的复杂性。9 T& B, V( E- o4 ~ W% d
5、模式适用环境
* }! z9 } S" i- {( O' Z在以下情况下可以使用迭代器模式:% _1 `4 k. E, H0 u) s! z
访问一个聚合对象的内容而无须暴露它的内部表示。& p- I! k: p! R2 ]
需要为聚合对象提供多种遍历方式。
' d7 \5 I# |8 ?( [0 V, o7 ?为遍历不同的聚合结构提供一个统一的接口。 * K T6 E9 L6 W# V
4 D1 W7 N3 v- d |