Iterator - 迭代器模式
定义

![]()
提供一个方法顺序訪问一个聚合对象中个各个元素,而又不须要暴露该对象的内部结构。
案例
一个聚合对象。如一个列表List。应该提供一种方法来让别人能够訪问它的元素。而又不用暴露内部结构。迭代器模式能够非常好的解决这类问题,关键思想就是将队列表的訪问和遍历从列表对象中分离出来,放到一个迭代器Iterator对象中。Iterator定义了一个訪问List对象的接口。
AbstractList提供了List的基本接口:
template<class Item>class AbstractList {public:virtual Iterator* createIterator() const = 0;virtual int count() const = 0;virtual void append(Item item) = 0;virtual void remove(Item item) = 0;virtual void get(Int index) = 0;};
在其子类中实现相关操作:
template<class Item>class ListOne : public AbstractList {public:virtual Iterator* createIterator() const;...};Iterator* ListOne::createIterator() {return new IteratorOne<Item>(this);}
Iterator类提供公有接口来支持迭代:
template<class Item>class Iterator {public:virtual void first() = 0;virtual void next() = 0;virtual bool isEnd() const = 0;virtual Item current() const = 0;proteced:Iterator();};
子类进行详细操作的实现:
template<class Item>class IteratorOne : public Iterator {public:IteratorOne(const ListOne<Item>* list);virtual void first();virtual void next();virtual bool isEnd() const;virtual Item current() const;private:ListOne<Item>* m_list;int m_index;};template<class Item>void IteratorOne::first() {m_index = 0;}template<class Item>void IteratorOne::next() {++m_index;}template<class Item>bool IteratorOne::isEnd() const {return m_index == m_list->count();}tempalte<class Item>Item IteratorOne::current() const {if(isEnd())throw IteratorOutOfBounds();return m_list->get(m_index);}
比方如今我们要打印Book类的一个List的书名:
ListOne<Book*> books;IteratorOne<Book*>* iter = books.createIterator();for(iter->first(); !iter->isEnd(); iter->next()) {std::cout << iter->current()->print();}delete iter;
这样实现必须保证每次迭代器都被删除,能够定义一个IteratorPtr来确保对象被释放:
template<class Item>class IteratorPtr {public:IteratorPtr(Iterator<Item>* iter) : m_iter(iter) {}~IteratorPtr() { delete m_iter; }Iterator<Item>* operator->() { returm m_iter; }Iterator<Item>* operator*() { return *m_iter; }private:Iterator<Item>* m_iter;}
ListOne<Book*> books;IteratorPtr<Book*> iter(books.createIterator());for(iter->first(); !iter->isEnd(); iter->next()) {std::cout << iter->current()->print();}
以上是迭代器的一种外部实现方式。另一种内部实现方式:
template<class Item>class ListTraverser {public:ListTravrerser(ListOne<Item>* list);void traverse();proteced:virtual void processItem(const Item&) = 0;private:IteratorOne<Item> m_iter;};void ListTraverser::traverse() {bool result = false;for(m_iter.first(); !m_iter.isEnd(); m_iter.next()) {processItem(m_item.current());}}
假设是Book对象的迭代操作,就能够定义一个BookTraverser类。实现processItem函数:
void BookTraverse::processItem(const Book* book) {cout << book;}
List<Book> books;BookTraverse bt(books);bt.traverse();
适用性
- 訪问一个集合对象的内容而无须要暴露它的内部展示
- 支持对集合对象的多种遍历
- 为遍历不同的集合结构提供一个统一的接口
浙公网安备 33010602011771号