In this recipe, we will implement our own iterator class, and then, we will iterate through it:
- First, we include the header, which enables us to print to the terminal:
#include <iostream>
- Our iterator class will be called num_iterator:
class num_iterator {
- Its only data member is an integer. That integer is used for counting. The constructor is for initializing it. It is generally a good form to make constructors explicit, which create a type from another type to avoid accidental implicit conversion. Note that we also provide a default value for position. This makes the instances of the num_iterator class default-constructible. Although we will not use the default constructor in the whole recipe, this is really important because some STL algorithms depend on iterators being default-constructible:
int i;
public:
explicit num_iterator(int position = 0) : i{position} {}
- When dereferencing our iterator (*it), it will emit an integer:
int operator*() const { return i; }
- Incrementing the iterator (++it) will just increment its internal counter, i:
num_iterator& operator++() {
++i;
return *this;
}
- A for loop will compare the iterator against the end iterator. If they are unequal, it will continue iterating:
bool operator!=(const num_iterator &other) const {
return i != other.i;
}
};
- That was the iterator class. We still need an intermediate object for writing for (int i : intermediate(a, b)) {...}, which then contains the begin and end iterator, which is preprogrammed to iterate from a to b. We call it num_range:
class num_range {
- It contains two integer members, which denote at which number the iteration shall start, and which number is the first number past the last number. This means if we want to iterate from 0 to 9, a is set to 0 and b to 10:
int a;
int b;
public:
num_range(int from, int to)
: a{from}, b{to}
{}
- There are only two member functions that we need to implement: the begin and end functions. Both return iterators that point to the beginning and the end of the numeric range:
num_iterator begin() const { return num_iterator{a}; }
num_iterator end() const { return num_iterator{b}; }
};
- That's it. We can use it. Let's write a main function which just iterates over a range that goes from 100 to 109 and prints all its values:
int main()
{
for (int i : num_range{100, 110}) {
std::cout << i << ", ";
}
std::cout << 'n';
}
- Compiling and running the program yields the following terminal output:
100, 101, 102, 103, 104, 105, 106, 107, 108, 109,