Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Custom Iterator in C++

Tags:

c++

iterator

stl

I have a class TContainer that is an aggregate of several stl collections pointers to TItems class.

I need to create an Iterator to traverse the elements in all the collections in my TContainer class abstracting the client of the inner workings.

What would be a good way to do this?. Should I crate a class that extends an iterator (if so, what iterator class should I extend), should I create an iterator class that is an aggregate of iterators?

I only need a FORWARD_ONLY iterator.

I.E, If this is my container:

typedef std::vector <TItem*> ItemVector; class TContainer {    std::vector <ItemVector *> m_Items; }; 

What would be a good Iterator to traverse all the items contained in the vectors of the m_Items member variable.

like image 201
Sugar Avatar asked May 08 '09 14:05

Sugar


People also ask

What is iterator in C?

An iterator is an object that allows you to step through the contents of another object, by providing convenient operations for getting the first element, testing when you are done, and getting the next element if you are not. In C, we try to design iterators to have operations that fit well in the top of a for loop.

How do I make an iterator class?

To create an Iterator class we need to override __next__() function inside our class i.e. __next__() function should be implemented in such a way that every time we call the function it should return the next element of the associated Iterable class. If there are no more elements then it should raise StopIteration.

What is a const iterator?

Constant Iterators:A const iterator points to an element of constant type which means the element which is being pointed to by a const_iterator can't be modified. Though we can still update the iterator (i.e., the iterator can be incremented or decremented but the element it points to can not be changed).


1 Answers

When I did my own iterator (a while ago now) I inherited from std::iterator and specified the type as the first template parameter. Hope that helps.

For forward iterators user forward_iterator_tag rather than input_iterator_tag in the following code.

This class was originally taken from istream_iterator class (and modified for my own use so it may not resemble the istram_iterator any more).

template<typename T> class <PLOP>_iterator          :public std::iterator<std::input_iterator_tag,       // type of iterator                                T,ptrdiff_t,const T*,const T&> // Info about iterator {     public:         const T& operator*() const;         const T* operator->() const;         <PLOP>__iterator& operator++();         <PLOP>__iterator operator++(int);         bool equal(<PLOP>__iterator const& rhs) const; };  template<typename T> inline bool operator==(<PLOP>__iterator<T> const& lhs,<PLOP>__iterator<T> const& rhs) {     return lhs.equal(rhs); } 

Check this documentation on iterator tags:
http://www.sgi.com/tech/stl/iterator_tags.html

Having just re-read the information on iterators:
http://www.sgi.com/tech/stl/iterator_traits.html

This is the old way of doing things (iterator_tags) the more modern approach is to set up iterator_traits<> for your iterator to make it fully compatible with the STL.

like image 182
Martin York Avatar answered Sep 20 '22 01:09

Martin York