当前位置: 首页 > article >正文

漫谈设计模式 [14]:迭代器模式

引导性开场

菜鸟:

最近在处理一个项目时,我遇到一个问题。我需要遍历一个集合中的元素,但集合的结构可能会变化。每次我都要写很多重复的代码,这让我很困惑。有没有更好的方法呢?

老鸟:

这个问题很常见。你有没有听说过迭代器模式?

菜鸟:

迭代器模式?听起来有点陌生,你能详细说说吗?

渐进式介绍概念

老鸟:

当然可以!我们先从一个生活中的例子开始。想象你有一本书,你想一页一页地阅读。你会一页一页地翻,而不是一次性把所有页都看完,对吧?迭代器模式就是这样的一个“翻页器”,它让你可以逐个处理集合中的元素,而不需要关心集合的内部结构。

菜鸟:

那听起来挺直观的。那这种模式的核心思想是什么呢?

老鸟:

核心思想很简单:通过提供一种方法,使你能够顺序地访问一个集合中的元素,而不需要暴露集合的内部表示。

Python代码示例,逐步展开

菜鸟:

那能给我一个简单的代码示例吗?

老鸟:

好的,我们先从一个最简单的例子开始。假设我们有一个列表,我们想要逐个访问它的元素。

class SimpleIterator:
    def __init__(self, collection):
        self._collection = collection
        self._index = 0

    def __next__(self):
        if self._index < len(self._collection):
            result = self._collection[self._index]
            self._index += 1
            return result
        else:
            raise StopIteration

    def __iter__(self):
        return self

# 使用示例
simple_list = [1, 2, 3, 4]
iterator = SimpleIterator(simple_list)

for item in iterator:
    print(item)

菜鸟:

我明白了,这个 SimpleIterator 通过 __next__ 方法遍历了集合中的每个元素。而 __iter__ 方法则返回了迭代器自身。

老鸟:

没错,这个就是最基础的迭代器实现。我们可以进一步扩展,让它支持更多类型的集合。

菜鸟:

那怎么扩展呢?

老鸟:

我们可以引入一个抽象的迭代器接口,然后为不同的集合类型实现不同的迭代器。

from abc import ABC, abstractmethod

class Iterator(ABC):
    @abstractmethod
    def __next__(self):
        pass

    @abstractmethod
    def __iter__(self):
        pass

class ListIterator(Iterator):
    def __init__(self, collection):
        self._collection = collection
        self._index = 0

    def __next__(self):
        if self._index < len(self._collection):
            result = self._collection[self._index]
            self._index += 1
            return result
        else:
            raise StopIteration

    def __iter__(self):
        return self

# 使用示例
list_collection = [1, 2, 3, 4]
list_iterator = ListIterator(list_collection)

for item in list_iterator:
    print(item)

菜鸟:

这样做的好处是什么呢?

老鸟:

通过引入接口和具体实现,我们就可以为不同的集合类型创建不同的迭代器,而使用者只需要与迭代器接口进行交互。

问题与反思

菜鸟:

如果不用迭代器模式,我会直接在集合类中实现遍历方法,这样也能实现功能呀。

老鸟:

确实可以,但这样会导致集合类承担过多的责任,违反单一责任原则。用迭代器模式,我们可以将遍历的逻辑与集合本身分开,使代码更清晰、更易维护。

菜鸟:

我明白了,这样可以让代码更具可读性和可维护性。

优势与适用场景

老鸟:

迭代器模式有很多优势。比如,它可以让你在不修改集合类的前提下,为其添加新的遍历方式。适用于需要对集合进行多种遍历操作的场景,如树形结构、图结构等。

菜鸟:

那现实生活中有哪些常见的应用场景呢?

老鸟:

比如文件系统的遍历,社交网络中的好友关系图遍历,甚至是游戏中的场景图遍历等。

常见误区与优化建议

菜鸟:

那在使用迭代器模式时,有没有什么常见的误区需要注意?

老鸟:

一个常见误区是:有些开发者在实现迭代器时,会在迭代器中修改集合本身,这样会导致意外的副作用。建议迭代器只负责遍历,而不修改集合。

总结与延伸阅读

老鸟:

今天我们聊了迭代器模式的核心思想、基本实现以及它的优势和适用场景。希望你对迭代器模式有了更深入的理解。接下来你可以阅读《设计模式:可复用面向对象软件的基础》这本书,了解更多设计模式。

菜鸟:

这次对话让我受益匪浅!我会继续学习其他设计模式,谢谢你!

老鸟:

不用客气!有问题随时来找我。


http://www.kler.cn/news/294923.html

相关文章:

  • 人工智能与机器学习原理精解【16】
  • Mac M1 安装Hadoop教程(安装包安装)
  • keepalived和lvs高可用集群
  • 一次关于生产环境服务无故宕机的排查过程
  • 顶刊精析|METI:整合细胞形态与空间转录组学的肿瘤微环境分析框架·24-09-06
  • MySQL面试题大全和详解,含SQL例子
  • EF框架删除数据
  • Hive是什么?
  • 模型压缩之剪枝
  • Openharmony 图片自适应全屏显示
  • C++系统教程002-数据类型(01)
  • pytorch torch.gather函数介绍
  • 运维工程师面试题--Linux加分项
  • Mysql(一) - 数据库操作, 表操作, CRUD
  • CMU 10423 Generative AI:lec3(阅读材料:GPT1论文解读)
  • 申万宏源证券完善金融服务最后一公里闭环,让金融服务“零距离、全天候”
  • 币安/欧易合约对冲APP系统开发
  • 【BuuCTF】BadySQli
  • C语言 | Leetcode C语言题解之第392题判断子序列
  • 小程序端pinia持久化
  • 2工作队列
  • 如何应对日益复杂的网络攻击?Edge SCDN(边缘安全加速)的应用场景探讨
  • 解决yarn安装依赖报错:certificate has expired at TLSSocket.onConnectSecure
  • 探索 MATLAB 中的 rem 函数:余数计算与应用
  • Find 方法、where 子句以及 AsNoTracking 方法各自有不同的用途和性能
  • 为libpng不同架构创建构建目录、编译、安装以及合并库文件的所有步骤。
  • python基础语法四-数据可视化
  • HTTP与HTTPS在软件测试中的解析
  • 使用modelsim小技巧
  • Mysql数据库表结构迁移PostgreSQL