C# 设计模式(行为型模式):迭代器模式
·
C# 设计模式(行为型模式):迭代器模式 (Iterator Pattern)
迭代器模式(Iterator Pattern)是一种行为型设计模式,用于顺序访问集合对象中的元素,而无需暴露集合的内部表示。它为各种集合类型提供了一种统一的遍历方式,使得用户可以在不考虑底层实现的情况下使用统一的接口来遍历集合。
一、什么是迭代器模式?
迭代器模式主要用于解决 “如何遍历集合中的元素” 这一问题。
通过将遍历逻辑抽象到一个迭代器对象中,它让集合的使用者可以专注于处理元素,而不需要关心集合的具体结构。
模式定义
提供一种方法,顺序访问一个聚合对象中的各个元素,而不需要暴露其内部表示。
二、迭代器模式的结构
迭代器模式包含以下关键角色:
-
Iterator(抽象迭代器)
- 定义访问和遍历元素的接口,如
MoveNext()和Current等方法。
- 定义访问和遍历元素的接口,如
-
ConcreteIterator(具体迭代器)
- 实现
Iterator接口,负责遍历集合中的元素。
- 实现
-
Aggregate(抽象聚合类)
- 定义创建迭代器的方法。
-
ConcreteAggregate(具体聚合类)
- 实现
Aggregate接口,返回集合对应的具体迭代器。
- 实现
三、适用场景
- 需要访问集合对象的内容,但不希望暴露集合的内部实现。
- 需要以多种方式遍历集合,例如正序、逆序或条件遍历。
- 需要为不同的集合提供统一的访问方式,如数组、列表、树等。
四、C# 中的迭代器模式实现
1. 示例场景
我们实现一个简单的自定义集合 BookCollection,用于存储书籍名称,并通过迭代器实现集合的遍历。
2. 实现代码
using System;
using System.Collections;
namespace IteratorPatternExample
{
// 抽象聚合类
interface IAggregate
{
IIterator CreateIterator();
}
// 抽象迭代器
interface IIterator
{
bool MoveNext(); // 移动到下一个元素
object Current { get; } // 获取当前元素
void Reset(); // 重置迭代器
}
// 具体聚合类
class BookCollection : IAggregate
{
private string[] books;
public BookCollection(string[] books)
{
this.books = books;
}
public IIterator CreateIterator()
{
return new BookIterator(this);
}
public int Count => books.Length;
public string this[int index] => books[index];
}
// 具体迭代器
class BookIterator : IIterator
{
private BookCollection collection;
private int currentIndex = -1;
public BookIterator(BookCollection collection)
{
this.collection = collection;
}
public bool MoveNext()
{
if (currentIndex + 1 < collection.Count)
{
currentIndex++;
return true;
}
return false;
}
public object Current => collection[currentIndex];
public void Reset()
{
currentIndex = -1;
}
}
// 客户端
class Program
{
static void Main(string[] args)
{
string[] books = { "C# 入门", "设计模式解析", "高效编程之道" };
var bookCollection = new BookCollection(books);
var iterator = bookCollection.CreateIterator();
Console.WriteLine("书籍列表:");
while (iterator.MoveNext())
{
Console.WriteLine(iterator.Current);
}
}
}
}
3. 运行结果
运行上述代码,输出如下:
书籍列表:
C# 入门
设计模式解析
高效编程之道
五、C# 内置迭代器模式
在 C# 中,迭代器模式已经被高度封装,IEnumerable 和 IEnumerator 接口是内置的迭代器模式支持。以下是对上述代码的简化版本,使用内置接口实现:
using System;
using System.Collections;
using System.Collections.Generic;
namespace IteratorPatternExample
{
// 具体聚合类
class BookCollection : IEnumerable<string>
{
private string[] books;
public BookCollection(string[] books)
{
this.books = books;
}
public IEnumerator<string> GetEnumerator()
{
foreach (var book in books)
{
yield return book;
}
}
IEnumerator IEnumerable.GetEnumerator()
{
return GetEnumerator();
}
}
class Program
{
static void Main(string[] args)
{
var books = new BookCollection(new[] { "C# 入门", "设计模式解析", "高效编程之道" });
Console.WriteLine("书籍列表:");
foreach (var book in books)
{
Console.WriteLine(book);
}
}
}
}
运行结果与上一版本相同,但代码更加简洁易懂。
六、优缺点分析
优点
- 解耦:客户端无需了解集合的内部实现,统一了访问接口。
- 灵活性:可以通过自定义迭代器实现多种遍历方式。
- 封装性:隐藏了集合的具体结构。
缺点
- 类数量增加:为每种集合实现迭代器可能会导致类数量增加。
- 性能开销:在一些大规模数据集合中,自定义迭代器可能会增加遍历开销。
七、实际应用场景
- 数据遍历:如列表、字典、队列等容器的遍历。
- 文件系统:遍历文件目录或文件内容。
- 图形界面:遍历 UI 控件树或可视元素集合。
八、总结
迭代器模式是一种强大的设计模式,它将集合的遍历操作与集合本身分离,提供了一种统一的访问方式。在 C# 中,迭代器模式已经通过 IEnumerable 和 IEnumerator 得到了内置支持,因此开发者通常不需要手动实现。但在某些特殊场景下,自定义迭代器仍然是一个有效的解决方案。
希望这篇文章能帮助你更好地理解迭代器模式!如果有任何疑问或建议,欢迎在评论区留言 😊!
更多推荐

所有评论(0)