C#设计模式系列:迭代器模式(Iterator)
迭代器模式把对象的职责分离,职责分离可以最大限度减少彼此之间的耦合程度,从而建立一个松耦合的对象。职责分离的要点是对被分离的职责进行封装,并以抽象的方式建立彼此之间的关系。
1、迭代器模式简介
1.1>、定义
迭代器模式提供一种方法可以顺序访问聚合对象中各个元素,但又不暴露该对象的内部表示。
1.2>、使用频率
高
2、迭代器模式结构
2.1>、结构图

2.2>、参与者
迭代器模式参与者:
◊ Iterator:迭代器定义访问和遍历元素的接口
◊ ConcreteIterator
° 具体迭代器实现迭代器接口
° 对该聚合遍历时跟踪当前位置
◊ Aggregate:聚合定义创建Iterator对象的接口
◊ ConcreteAggregate:具体聚合,实现相应迭代器的接口,返回具体迭代器的一个适当的实例。
在迭代器模式中,ConcreteAggregate通过Aggregate定义的接口得到Iterator,并且这是一个ConcreteIterator,该ConcreteIterator具体实现了对ConcreteAggregate的访问与遍历的方法。通过ConcreteIterator可以访问并使用集合中的元素。
3、迭代器模式结构实现

Iterator.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.IteratorPattern.Structural
{
public abstract class Iterator
{
public abstract object First();
public abstract object Next();
public abstract bool IsDone();
public abstract object CurrentItem();
}
}
Aggregate.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.IteratorPattern.Structural
{
public abstract class Aggregate
{
public abstract Iterator CreateIterator();
}
}
ConcreteAggregate.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; using System.Collections; namespace DesignPatterns.IteratorPattern.Structural
{
public class ConcreteAggregate : Aggregate
{
private ArrayList _items = new ArrayList(); public override Iterator CreateIterator()
{
return new ConcreteIterator(this);
} public int Count
{
get { return _items.Count; }
} public object this[int index]
{
get { return _items[index]; }
set { _items.Insert(index, value); }
}
}
}
ConcreteIterator.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.IteratorPattern.Structural
{
public class ConcreteIterator : Iterator
{
private ConcreteAggregate _aggregate;
private int _current = ; public ConcreteIterator(ConcreteAggregate aggregate)
{
this._aggregate = aggregate;
} public override object First()
{
return _aggregate[];
} public override object Next()
{
object ret = null;
if (_current < _aggregate.Count - )
{
ret = _aggregate[++_current];
} return ret;
} public override object CurrentItem()
{
return _aggregate[_current];
} public override bool IsDone()
{
return _current >= _aggregate.Count;
}
}
}
Program.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; using DesignPatterns.IteratorPattern.Structural; namespace DesignPatterns.IteratorPattern
{
class Program
{
static void Main(string[] args)
{
ConcreteAggregate a = new ConcreteAggregate();
a[] = "Item A";
a[] = "Item B";
a[] = "Item C";
a[] = "Item D"; ConcreteIterator i = new ConcreteIterator(a); Console.WriteLine("Iterating over collection:");
object item = i.First();
while (item != null)
{
Console.WriteLine(item);
item = i.Next();
}
}
}
}
运行输出:
Iterating over collection:
Item A
Item B
Item C
Item D
请按任意键继续. . .
4、迭代器模式实践应用
在迭代器模式的设计中,有两种具体的实现方式,分别为外禀迭代器和内禀迭代器。白箱聚集与外禀迭代器:白箱聚集向外界提供访问自己内部元素的接口,从而使得外禀迭代器可以通过聚集提供的方法实现迭代功能。黑箱聚集与内禀迭代器:黑箱聚集不向外界提供遍历自己内部元素的接口,因此聚集的成员只能被聚集内部的方法访问。由于内禀迭代器恰好也是聚集的成员,因此可以访问聚集元素。
4.1、外禀迭代器
外禀迭代器的迭代过程使用了集合中的元素,通过集合向外界提供了访问自身内部元素的机会。

Iterator.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.IteratorPattern.Practical.ExtrinsicIterator
{
/// <summary>
/// 定义一个迭代器接口
/// </summary>
public interface Iterator
{
/// <summary>
/// 迭代器定位到聚合的第一个元素
/// </summary>
void First(); /// <summary>
/// 遍历下一个
/// </summary>
void Next(); /// <summary>
/// 判断是否完成遍历
/// </summary>
/// <returns></returns>
bool IsDone(); /// <summary>
/// 获得当前遍历的项
/// </summary>
/// <returns></returns>
object CurrentItem();
}
}
ConcreteIterator.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.IteratorPattern.Practical.ExtrinsicIterator
{
/// <summary>
/// 定义具体的迭代器类
/// </summary>
public class ConcreteIterator : Iterator
{
private ConcreteAggregate aggregate;
private int index = ;
private int size = ; /// <summary>
/// 根据不同的聚合类进行初始化
/// </summary>
/// <param name="aggregate"></param>
public ConcreteIterator(ConcreteAggregate aggregate)
{
this.aggregate = aggregate;
size = aggregate.Size();
index = ;
} public void First()
{
index = ;
} public void Next()
{
if (index < size)
{
index++;
}
} /// <summary>
/// 判断是否遍历完毕
/// </summary>
/// <returns></returns>
public bool IsDone()
{
return index >= size;
} /// <summary>
/// 获取当前遍历的元素
/// </summary>
/// <returns></returns>
public object CurrentItem()
{
return aggregate.GetElement(index);
}
}
}
Aggregate.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.IteratorPattern.Practical.ExtrinsicIterator
{
/// <summary>
/// 定义一个抽象的聚合类
/// </summary>
public abstract class Aggregate
{
/// <summary>
/// 只有一个功能,创建迭代器
/// </summary>
/// <returns></returns>
public virtual Iterator CreateIterator()
{
return null;
}
}
}
ConcreteAggregate.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.IteratorPattern.Practical.ExtrinsicIterator
{
/// <summary>
/// 定义一个具体的聚合类
/// </summary>
public class ConcreteAggregate : Aggregate
{
// 存储元素的集合
private object[] objs = { "Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday" }; /// <summary>
/// 获得元素个数
/// </summary>
/// <returns></returns>
public int Size()
{
return objs.Length;
} /// <summary>
/// 获取指定序号的元素
/// </summary>
/// <param name="index">指定的序号</param>
/// <returns></returns>
public object GetElement(int index)
{
if (index < || index > objs.Length)
{
return null;
} return objs[index];
} /// <summary>
/// 创建该聚合类的迭代器
/// </summary>
/// <returns></returns>
public override Iterator CreateIterator()
{
return new ConcreteIterator(this);
}
}
}
Client.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.IteratorPattern.Practical.ExtrinsicIterator
{
public class Client
{
private Iterator _iterator;
private Aggregate _aggregate = new ConcreteAggregate(); public void Operation()
{
// 获得迭代器
_iterator = _aggregate.CreateIterator(); while (!_iterator.IsDone())
{
Console.WriteLine(_iterator.CurrentItem());
_iterator.Next();
}
} static void Main(string[] args)
{
Client client = new Client();
client.Operation();
}
}
}
运行输出:
Sunday
Monday
Tuesday
Wednesday
Thursday
Friday
Saturday
请按任意键继续. . .
4.2、内禀迭代器
内禀迭代器实现的关键是在集合的内部定义一个私有的具体迭代子类,由它来负责迭代器的所有功能。因为它是集合的私有类,所以它的对象可以遍历集合的内部元素,实现迭代器定义的所有接口,而集合本身并未向外界提供访问自己内部元素的接口。

Iterator.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.IteratorPattern.Practical.IntrinsicIterator
{
/// <summary>
/// 定义一个迭代器接口
/// </summary>
public interface Iterator
{
/// <summary>
/// 迭代器定位到聚合的第一个元素
/// </summary>
void First(); /// <summary>
/// 遍历下一个
/// </summary>
void Next(); /// <summary>
/// 判断是否完成遍历
/// </summary>
/// <returns></returns>
bool IsDone(); /// <summary>
/// 获得当前遍历的项
/// </summary>
/// <returns></returns>
object CurrentItem();
}
}
Aggregate.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.IteratorPattern.Practical.IntrinsicIterator
{
/// <summary>
/// 定义一个抽象的聚合类
/// </summary>
public abstract class Aggregate
{
/// <summary>
/// 只有一个功能,创建迭代器
/// </summary>
/// <returns></returns>
public virtual Iterator CreateIterator()
{
return null;
}
}
}
ConcreteAggregate.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.IteratorPattern.Practical.IntrinsicIterator
{
/// <summary>
/// 定义一个具体的聚合类
/// </summary>
public class ConcreteAggregate : Aggregate
{
// 存储元素的集合
private static object[] objs = { "Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday" }; /// <summary>
/// 定义具体的迭代器类
/// </summary>
private class ConcreteIterator : Iterator
{
private int _index = ; public void First()
{
_index = ;
} public void Next()
{
if (_index < objs.Length)
{
_index++;
}
} public bool IsDone()
{
return _index == objs.Length;
} public object CurrentItem()
{
return objs[_index];
}
} /// <summary>
/// 获得元素个数
/// </summary>
/// <returns></returns>
public int Size()
{
return objs.Length;
} /// <summary>
/// 获取指定序号的元素
/// </summary>
/// <param name="index">指定的序号</param>
/// <returns></returns>
public object GetElement(int index)
{
if (index < || index > objs.Length)
{
return null;
} return objs[index];
} /// <summary>
/// 创建该聚合类的迭代器
/// </summary>
/// <returns></returns>
public override Iterator CreateIterator()
{
return new ConcreteIterator();
}
}
}
Client.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.IteratorPattern.Practical.IntrinsicIterator
{
public class Client
{
private Iterator _iterator;
private Aggregate _aggregate = new ConcreteAggregate(); public void Operation()
{
// 获得迭代器
_iterator = _aggregate.CreateIterator(); while (!_iterator.IsDone())
{
Console.WriteLine(_iterator.CurrentItem());
_iterator.Next();
}
} static void Main(string[] args)
{
Client client = new Client();
client.Operation();
}
}
}
5、迭代器模式应用分析
迭代器模式适用情形:
1>、访问一个具体对象的内容而不暴露它的内部表示;
2>、支持对聚合对象的多种遍历;
3>、为遍历不同的聚合结构提供一个统一的接口(即支持多态迭代)。
迭代器模式特点:
1>、简化聚集的行为,迭代器具备了遍历的接口,这样聚集的接口就不必具备遍历接口;
2>、每一个聚集对象都可以有一个或者更多的迭代器对象,每一个迭代器的迭代状态可以彼此独立(外禀迭代器);
3>、遍历算法被封装到迭代器对象中,迭代算法可以独立于聚集对象变化。Client不必知道聚集对象的类型,通过迭代器可以就读取和遍历聚集对象。这样的好处是聚集本身内部数据发生变化而不影响Client的程序。
C#设计模式系列:迭代器模式(Iterator)的更多相关文章
- 乐在其中设计模式(C#) - 迭代器模式(Iterator Pattern)
原文:乐在其中设计模式(C#) - 迭代器模式(Iterator Pattern) [索引页][源码下载] 乐在其中设计模式(C#) - 迭代器模式(Iterator Pattern) 作者:weba ...
- 设计模式学习--迭代器模式(Iterator Pattern)和组合模式(Composite Pattern)
设计模式学习--迭代器模式(Iterator Pattern) 概述 ——————————————————————————————————————————————————— 迭代器模式提供一种方法顺序 ...
- 二十四种设计模式:迭代器模式(Iterator Pattern)
迭代器模式(Iterator Pattern) 介绍提供一种方法顺序访问一个聚合对象中各个元素,而又不需暴露该对象的内部表示. 示例有一个Message实体类,某聚合对象内的各个元素均为该实体对象,现 ...
- [设计模式] 16 迭代器模式 Iterator Pattern
在GOF的<设计模式:可复用面向对象软件的基础>一书中对迭代器模式是这样说的:提供一种方法顺序访问一个聚合对象中各个元素,而又不需要暴露该对象的内部表示. 类图和实例: 迭代器模式由以下角 ...
- 设计模式之迭代器模式(Iterator)摘录
23种GOF设计模式一般分为三大类:创建型模式.结构型模式.行为模式. 创建型模式抽象了实例化过程,它们帮助一个系统独立于怎样创建.组合和表示它的那些对象.一个类创建型模式使用继承改变被实例化的类,而 ...
- 设计模式 笔记 迭代器模式 Iterator
//---------------------------15/04/26---------------------------- //Iterator 迭代器模式----对象行为型模式 /* 1:意 ...
- 行为型设计模式之迭代器模式(Iterator)
结构 意图 提供一种方法顺序访问一个聚合对象中各个元素, 而又不需暴露该对象的内部表示. 适用性 访问一个聚合对象的内容而无需暴露它的内部表示. 支持对聚合对象的多种遍历. 为遍历不同的聚合结构提供一 ...
- 设计模式之迭代器模式 Iterator
代码实现 public interface MyIterator { void first(); //将游标指向第一个元素 void next(); //将游标指向下一个元素 boolean hasN ...
- Java 设计模式系列(十五)迭代器模式(Iterator)
Java 设计模式系列(十五)迭代器模式(Iterator) 迭代器模式又叫游标(Cursor)模式,是对象的行为模式.迭代子模式可以顺序地访问一个聚集中的元素而不必暴露聚集的内部表象(interna ...
- 设计模式系列之迭代器模式(Iterator Pattern)——遍历聚合对象中的元素
模式概述 模式定义 模式结构图 模式伪代码 模式改进 模式应用 模式在JDK中的应用 模式在开源项目中的应用 模式总结 说明:设计模式系列文章是读刘伟所著<设计模式的艺术之道(软件开发人员内功修 ...
随机推荐
- 【Oracle】dba_jobs字段说明
dba_jobs 1 字段(列) 数据类型 描述 JOB NUMBER 任务的唯一标示号 LOG_USER ) 提交任务的用户 PRIV_USER ) 赋予任务权限的用户 SCHEMA_USER ) ...
- Python for Infomatics 第13章 网页服务二(译)
注:文章原文为Dr. Charles Severance 的 <Python for Informatics>.文中代码用3.4版改写,并在本机测试通过. 13.4 JavaScript ...
- monodroid 调用 JNI Native 的一些问题
在Android版本开发的过程中,需要使用一些用JNI开发的NDK的native库.这里谈一谈踩到的坑,给大家参考. 虽然java的程序我还算熟悉,但是没有了解过 JNI Native 的开发,一般是 ...
- jquery+bootstrap实现tab切换, 每次切换时都请求数据, 点击提交分别向不同的地址提交数据
今天一个朋友叫帮做一个tab切换, 每一个tab内容区域都是从后台取出的数据, 这些数据要用表格的形式显示处理, 并且表格的内容区域可以修改, 如下所示: 例子查看请演示查看. 截图如图所示: 实现步 ...
- 整理ViewController的生命周期和加载过程
按照执行顺序排列 - initWithCoder:通过nib文件初始化时触发 - awakeFromNib:nib文件被加载的时候,会发送一个awakeFromNib的消息到nib文件中的每个对象 p ...
- oracle plsql 无法连接 报 ORA-12560: TNS:protocol adapter error
ORA-12560: TNS:protocol adapter error 添加一个环境变量,名为TNS_ADMIN,值为 tnsnames.ora 文件所在路径.比如我的本机为:D:/instant ...
- thrift笔记
Thrift tutorial 演示 python服务端与客户端本文的开发环境是windows 7 + python2.7.3Thrift官方主页:http://thrift.apache.org/先 ...
- 一些值得练习的github项目
简单粗暴,一晚上用 node.Vue 写个联机五子棋 https://github.com/ccforward/cc/issues/51 Vue2.0实现简易豆瓣电影webApp https://gi ...
- Your awesome titleHH
Welcome to Jekyll! Your awesome titleHH About Blogging Like a Hacker Welcome to Jekyll! Jan 9, 2016 ...
- 在 Azure 上使用 Docker运行 Mono
Docker 是最近相当热门的一个名词,它是一个基于 Linux Container 的轻量化的虚拟技术,而微软也相当积极与 Docker 合作,在 Azure 上支持这个火热的技术,并且提供简单的方 ...