文章目录
- 🔄 迭代器模式(Iterator Pattern)深度解析
- 一、模式本质与核心价值
- 二、经典UML结构
- 三、Unity实战代码(背包系统遍历)
- 1. 定义迭代器与聚合接口
- 2. 实现具体聚合类(背包物品集合)
- 3. 实现具体迭代器
- 4. 客户端使用
- 四、模式进阶技巧
- 1. 过滤迭代器(按类型遍历)
- 2. 协程分帧遍历
- 3. 双向迭代器
- 五、游戏开发典型应用场景
- 六、性能优化策略
- 七、模式对比与选择
- 八、最佳实践原则
- 九、常见问题解决方案
🔄 迭代器模式(Iterator Pattern)深度解析
——以Unity实现高效集合遍历与动态场景管理为核心案例
一、模式本质与核心价值
核心目标:
✅ 统一集合遍历接口,无需暴露内部数据结构
✅ 支持多种遍历方式(顺序、逆序、过滤等)
✅ 解耦集合结构与遍历算法,提升代码扩展性
关键术语:
- Iterator(迭代器接口):定义遍历操作(Next、HasNext等)
- ConcreteIterator(具体迭代器):实现特定遍历逻辑
- Aggregate(聚合接口):定义创建迭代器的方法
- ConcreteAggregate(具体聚合):实现集合数据结构
数学表达:
设集合C有元素{e₁, e₂, …, eₙ},迭代器I满足:
I© → e₁ → e₂ → … → eₙ
二、经典UML结构
三、Unity实战代码(背包系统遍历)
1. 定义迭代器与聚合接口
public interface IIterator<T> {bool HasNext();T Next();void Reset();
}public interface IAggregate<T> {IIterator<T> CreateIterator();int Count { get; }T this[int index] { get; }
}
2. 实现具体聚合类(背包物品集合)
public class Inventory : IAggregate<Item> {private List<Item> _items = new();public void AddItem(Item item) => _items.Add(item);public IIterator<Item> CreateIterator() => new InventoryIterator(this);public int Count => _items.Count;public Item this[int index] => _items[index];
}
3. 实现具体迭代器
public class InventoryIterator : IIterator<Item> {private Inventory _inventory;private int _index;public InventoryIterator(Inventory inventory) {_inventory = inventory;_index = -1;}public bool HasNext() => _index < _inventory.Count - 1;public Item Next() => _inventory[++_index];public void Reset() => _index = -1;
}
4. 客户端使用
public class InventoryUI : MonoBehaviour {[SerializeField] private Inventory _inventory;void Update() {if(Input.GetKeyDown(KeyCode.I)) {StartCoroutine(DisplayItems());}}private IEnumerator DisplayItems() {var iterator = _inventory.CreateIterator();while(iterator.HasNext()) {Item item = iterator.Next();Debug.Log($"物品:{item.Name}");yield return null; // 分帧显示避免卡顿}}
}
四、模式进阶技巧
1. 过滤迭代器(按类型遍历)
public class WeaponIterator : IIterator<Item> {private IIterator<Item> _baseIterator;public WeaponIterator(Inventory inventory) {_baseIterator = inventory.CreateIterator();}public bool HasNext() {while(_baseIterator.HasNext()) {if(_baseIterator.Next() is Weapon) {_baseIterator.ResetToPrevious();return true;}}return false;}public Item Next() => _baseIterator.Next();
}
2. 协程分帧遍历
public static class IteratorExtensions {public static IEnumerator CoIterate<T>(this IIterator<T> iterator, Action<T> action) {while(iterator.HasNext()) {action(iterator.Next());yield return null; // 每帧处理一个元素}}
}// 使用示例
StartCoroutine(_inventory.CreateIterator().CoIterate(item => {// 处理每个物品
}));
3. 双向迭代器
public interface IBidirectionalIterator<T> : IIterator<T> {bool HasPrevious();T Previous();
}public class InventoryBidirectionalIterator : IBidirectionalIterator<Item> {// 实现前后遍历逻辑
}
五、游戏开发典型应用场景
-
场景对象管理
public class SceneObjectManager : IAggregate<GameObject> {private List<GameObject> _objects = new();public IIterator<GameObject> CreateIterator() => new SceneObjectIterator(this); }
-
技能效果链
public class SkillEffectChain : IAggregate<IEffect> {public IIterator<IEffect> CreateReverseIterator() {return new ReverseEffectIterator(this);} }
-
AI决策评估
public class AIEvaluator {public void EvaluateAll(IIterator<AICondition> conditions) {while(conditions.HasNext()) {var condition = conditions.Next();condition.Evaluate();}} }
-
动态生成系统
public class WorldGenerator {public void GenerateChunks(IIterator<Vector3> positionIterator) {while(positionIterator.HasNext()) {GenerateChunkAt(positionIterator.Next());}} }
六、性能优化策略
策略 | 实现方式 | 适用场景 |
---|---|---|
批处理迭代 | 每次处理多个元素 | 大规模数据集 |
缓存迭代器 | 复用迭代器实例 | 频繁遍历操作 |
惰性求值 | 需要时再计算元素 | 复杂对象集合 |
空间分区 | 结合四叉树/八叉树 | 3D场景遍历 |
七、模式对比与选择
维度 | 迭代器模式 | 访问者模式 |
---|---|---|
关注点 | 遍历机制 | 数据操作 |
扩展性 | 新增迭代方式 | 新增操作类型 |
数据结构耦合 | 低耦合 | 需要接受访问者接口 |
典型场景 | 集合遍历 | 复杂数据结构操作 |
八、最佳实践原则
- 单一职责原则:迭代器只关注遍历逻辑
- 不可变快照:在迭代过程中防止集合修改
public class SnapshotIterator<T> : IIterator<T> {private readonly T[] _snapshot;// 基于快照的迭代实现... }
- 异常处理:处理边界条件
public T Next() {if(!HasNext()) throw new InvalidOperationException("No more elements");// ... }
- 资源释放:实现IDisposable接口
public class FileLineIterator : IIterator<string>, IDisposable {private StreamReader _reader;public void Dispose() => _reader?.Dispose(); }
九、常见问题解决方案
Q1:如何避免遍历时集合被修改?
→ 使用读写锁或副本迭代
public class ThreadSafeIterator<T> : IIterator<T> {private ReaderWriterLockSlim _lock;// 在Next/HasNext中加读锁...
}
Q2:如何实现复杂条件过滤?
→ 使用组合过滤器
public class CompositeFilterIterator<T> : IIterator<T> {private List<Predicate<T>> _filters = new();public void AddFilter(Predicate<T> filter) {_filters.Add(filter);}public bool HasNext() {while(_baseIterator.HasNext()) {var item = _baseIterator.Peek();if(_filters.All(f => f(item))) return true;_baseIterator.Next();}return false;}
}
Q3:如何优化大型场景遍历性能?
→ 实现空间分区迭代器
public class QuadTreeIterator : IIterator<GameObject> {private QuadTree _quadTree;private List<QuadTreeNode> _nodeStack = new();public bool HasNext() {while(_nodeStack.Count > 0) {var current = _nodeStack.Last();if(current.HasChildren) {// 处理子节点...} else {return current.Objects.Count > 0;}}return false;}
}
上一篇 【行为型之解释器模式】游戏开发实战——Unity动态公式解析与脚本系统的架构奥秘
下一篇 【行为型之中介者模式】游戏开发实战——Unity复杂系统协调与通信架构的核心秘诀