意图:
提供一种方法顺序访问一个聚合对象中各个元素,而又不需要暴露该对象的内部表示。
适用性:
1访问一个聚合对象的内容而无需暴露它的内部表示
2支持对聚合对象的多种遍历
3为遍历不同的聚合结构提供一个统一的接口
效果:
1它支持以不同的方式遍历一个聚合
2简化聚合的接口
3在同一个聚合上可以有多个遍历
实现:
1谁控制该迭代
当客户来控制该迭代时,该迭代器称为外部迭代器。客户主动的推进遍历的步伐。
当由迭代器内部控制迭代时,该迭代器称为外部迭代器。客户只需要提交一个待执行的操作,而迭代器将对聚合中的每一个元素实施该操作
2谁定义遍历算法
聚合本身可以定义遍历算法
迭代器负责遍历算法,易于在相同的聚合上使用不同的迭代算法,也易于在不同的聚合上重用相同的算法
3迭代器的健壮性 一个健壮的迭代器保证插入和删除操作不会干扰遍历,且不需拷贝该聚合
4附加的迭代器操作 迭代器的最小接口由First,Next,IsDone和CurrentItem组成,可附加一些其他可用的操作。
5在C++中使用多态的迭代器 用一个Factory Method动态的分配迭代器对象。
多态迭代器有一个缺点:客户必须负责删除它们,有一个补救方法是,适用一个栈分配的Proxy作为实际迭代器的中间代理,该代理在其析构器中删除该迭代器
Interator.h
- #include <iostream>
- using namespace std;
- class Employee
- {
- public:
- Employee(const char* name,int age):_name(name),_age(age){}
- ~Employee(){cout<<"An employee is destroyed"<<endl;}
- void print(){cout<<"The employee name is "<<_name<<" and the age is "<<_age<<endl;}
- private:
- const char* _name;
- int _age;
- };
- template <class Item>
- class List
- {
- public:
- List(long size = 0):_size(size)
- {
- cout<<"A list is created"<<endl;
- }
- long Count() const {return _size;}
- typedef struct Node
- {
- Node(){}
- Item item;
- Node* next;
- Node* prev;
- } Node;
- Item Get(long index) const
- {
- long i =0;
- Node* p = itemlist;
- for (i =0;i<index;i++)
- p = p->next;
- return (p->item);
- }
- Node* End() const
- {
- Node* p = itemlist;
- if ((p->next == NULL)&&(p->prev == NULL))
- return p;
- while(p->next != NULL)
- {
- p= p->next;
- }
- return p;
- }
- void Append(const Item& item)
- {
- //Node* end = End();
- Node* a = new Node;
- a->item = item;
- a->next = NULL;
- if (_size == 0)
- {
- a->prev = NULL;
- itemlist = a;
- }
- else
- {
- End()->next = a;
- a->prev = End();
- }
- _size ++;
- }
- private:
- long _size;
- Node* itemlist;
- };
- template <class Item>
- class Iterator
- {
- public:
- virtual void First() = 0;
- virtual void Next() = 0;
- virtual bool IsDone() const=0;
- virtual Item CurrentItem() const=0;
- protected:
- Iterator(){}
- };
- template <class Item>
- class ListIterator:public Iterator<Item>
- {
- public:
- ListIterator(List <Item>* aList)
- {
- _list = aList;
- _current = 0;
- }
- virtual void First() {_current=0;}
- virtual void Next() {_current++;}
- virtual bool IsDone() const
- { return _current >= _list->Count();}
- virtual Item CurrentItem() const
- {
- if (IsDone())
- {
- return 0;
- }
- else
- return _list->Get(_current);
- }
- private:
- List<Item>* _list;
- long _current;
- };
main.cpp
- #include "Iterator.h"
- #include <iostream>
- using namespace std;
- void PrintEmployees(ListIterator<Employee*>& i)
- {
- for(i.First();!i.IsDone();i.Next())
- if (i.CurrentItem()!= 0)
- (i.CurrentItem())->print();
- }
- int main()
- {
- List<Employee*>* employees = new List<Employee*>;
- Employee* e1= new Employee("11",11);
- Employee* e2 = new Employee("22",22);
- employees->Append(e1);
- employees->Append(e2);
- ListIterator<Employee*> forward(employees);
- //ListIterator<Employee*>* forward;
- //forward = new ListIterator<Employee*>(employees);
- PrintEmployees(forward);
- List<int> a;
- int b =1;
- int c=1;
- a.Append(b);
- a.Append(c);
- return 0;
- }