C++实现对象行为型-迭代器模式

1.1 基本概念

迭代器模式(Iterator Pattern):提供了一种方法来访问聚合对象,而不用暴露这个对象的内部。

聚合对象的两个基本功能:

(1)存储内部数据;

(2)遍历内部数据;

1.2 模式结构

 (1)Iterator(抽象迭代器)

抽象迭代器定义了访问和变量 元素的接口,用于获取第一个元素的first(),访问下一个元素的next(),用于获取当前元素的current()。

 (2)ConcreteIterator(具体迭代器)

具体迭代器实现了抽象迭代器接口,完成对聚合对象的遍历,同时在对聚合进行遍历时跟踪其当前位置

(3)Aggregate(抽象聚合类或称抽象容器)

抽象聚合类用于存储对象,并定义创建相应迭代器对象的接口,声明一个 createIterator() 方法,用于创建一个迭代器对象。

(4)ConcreteAggregate(具体聚合类或称具体容器)

具体聚合类实现了创建相应迭代器的接口,实现了在聚合类中声明的 createIterator() 方法,该方法返回一个对应的具体迭代器实例。

  1. 容器部分,内部可以存放一系列数据,并提供迭代器调用接口。
  2. 迭代器部分,内部含有对容器部分的调用,并获得容器内部提供的方法。

具体容器和具体迭代器两者是相互调用的,也就是说容器调用了迭代器,然后通过迭代器调用了容器内部自身的方法来实现封装。

1.3 优缺点

优点:

(1)支持以不同的方式遍历一个聚合对象。迭代器可以提供多种遍历方式,比如说对有序列表,我们可以根据需要提供正序遍历,倒序遍历两种迭代器,用户用起来只需要得到我们实现好的迭代器,就可以方便的对集合进行遍历了。同时其封装性良好,用户只需要得到迭代器就可以遍历,而对于遍历算法则不用去关心

(2)在迭代器模式中,增加新的聚合类和迭代器都很方便,不需要修改原有代码,满足开闭原则;

缺点:

由于存储数据和遍历数据的职责分离,增加新的聚合类需要对应增加新的迭代器类,类的个数成对增加,一定程度上增加了系统的复杂性。

1.4 应用场景

(1)访问一个聚合对象的内容而无须暴露它的内部表示。将聚合对象的访问与内部数据的存储分离,使得访问聚合对象时,无须了解其内部实现细节;

(2)需要为聚合对象提供多种遍历方式;

(3)为遍历不同的聚合结构提供一个统一的接口。

1.5 举例

电视机遥控器可以看做一个迭代器实例,电视机遥控器可以实现对电视机频道集合的遍历操作。

#include<iostream>
#include <vector>
#include <string>
// 具体处理者 Department manager

using namespace std;
#define SAFE_DELETE(p) if (p) { delete p; p = NULL; }

/**
* @brief TVIterator 电视机遥控器类
* @brief (抽象迭代器类) 声明迭代器所具有的方法
*/
class TVIterator
{
public:
    TVIterator(){};
    virtual ~TVIterator(){};
    virtual string First() = 0;
    virtual string Next() = 0;
    virtual string GetCur() = 0;
    virtual bool IsEnd() = 0;
};

/**
* @brief TelevisionAggregate 电视机类
* @brief 抽象聚合类 声明用于创建 具体迭代器对象的CreateIterator() 方法
*/
class TelevisionAggregate
{
public:
 TelevisionAggregate(){};
    virtual ~TelevisionAggregate(){};
    virtual int Count() = 0;
    virtual void Push(const string &strValue) = 0;
    virtual string Pop(const int index) = 0;
    virtual TVIterator *CreateIterator() = 0;
};

/**
* @brief TclTVIterator 具体聚合类
* @brief 具体迭代器类
*/
class TclTVIterator : public TVIterator
{
public:
 TclTVIterator(TelevisionAggregate *pAggregate) : TVIterator()
    {
        m_nCurrent = 0;
        m_Aggregate = pAggregate;
    }

    string First()
    {
        return m_Aggregate->Pop(0);
    }
string Next()
    {
        string strRet;
        m_nCurrent++;

        if(m_nCurrent < m_Aggregate->Count())
        {
            strRet = m_Aggregate->Pop(m_nCurrent);
        }

        return strRet;
    }

string GetCur()
    {
        return m_Aggregate->Pop(m_nCurrent);
    }

    bool IsEnd()
    {
        return ((m_nCurrent >= m_Aggregate->Count()) ? true : false);
    }

private:
    int m_nCurrent;
    TelevisionAggregate *m_Aggregate;
};

/**
* @brief TclTelevisionAggregate TCL电视机类
* @brief 具体聚合类
*/
class TclTelevisionAggregate : public TelevisionAggregate
{
public:
TclTelevisionAggregate() : m_pIterator(NULL)
    {
        m_vecItems.clear();
    }

    ~TclTelevisionAggregate()
    {
        if(m_pIterator != NULL)
        {
            delete m_pIterator;
            m_pIterator = NULL;
        }
    }
 TVIterator *CreateIterator()
    {
        if(m_pIterator == NULL)
        {
            m_pIterator = new TclTVIterator(this);
        }

        return m_pIterator;
    }

 int Count()
    {
        return m_vecItems.size();
    }

    void Push(const string &strValue)
    {
        m_vecItems.push_back(strValue);
    }

    string Pop(const int index)
    {
        string strRet;

        if(index < Count())
        {
            strRet = m_vecItems[index];
        }

        return strRet;
    }

private:
    TVIterator *m_pIterator;
    vector<string> m_vecItems;
};

int main(int argc, char **argv)
{
    TclTelevisionAggregate *pTclTelevision = new TclTelevisionAggregate();
    if(pTclTelevision == NULL)
        return -1;

    pTclTelevision->Push("CCTV-1");
    pTclTelevision->Push("CCTV-2");
    pTclTelevision->Push("CCTV-3");
TVIterator *iter = NULL;
    iter = pTclTelevision->CreateIterator();

    if(iter != NULL)
{
        string strItem = iter->First();

        while(!iter->IsEnd())
        {
            cout << iter->GetCur() << " is ok" << endl;
            iter->Next();
        }
    }

SAFE_DELETE(pTclTelevision);
	//SAFE_DELETE(iter);

    return 0;
}

参考文献:

【1】C++之迭代器(Iterator)模式 - 古月居

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值