迭代器使用起来非常方便,其实背后做了大量的工作。它是容器类的一个内嵌类,管理着一个指向容器类元素的指针。

#include<iostream>
#include<string>
#include<assert.h>
using std::cout;
using std::endl;
using std::string;
struct TestType{
    string word;
    TestType(string str = "") : word(str){}
};
template<class T>
class Stack {
    struct Link {
        T data;
        Link* next;
        Link(T dat, Link* nxt)
            : data(dat), next(nxt) {}
    }* head;
public:
    Stack() : head(0) {
        cout << "Stack default contructor\n";
     }
    ~Stack();
    void push(const T& dat) {
        cout << "Stack::" << __FUNCTION__ << "\n";
        head = new Link(dat, head);
    }
    T& peek() const {
        cout << "Stack::" << __FUNCTION__ << "\n";
        assert(head);
        return head->data;
    }
    T pop();
    // Nested iterator class:
    class iterator; // Declaration required
    friend class iterator; // Make it a friend
    class iterator { // Now define it
        Stack::Link* p;
    public:
        iterator(const Stack<T>& tstack) : p(tstack.head) {
            cout << "iterator::" << __FUNCTION__ << "(const Stack<T>& tstack)\n";
        }
        // Copy-constructor:
        iterator(const iterator& it) : p(it.p) {
            cout << "iterator::" << __FUNCTION__ << "(const iterator& it)\n";
        }
        // The end sentinel iterator:
        iterator() : p(0) {
            cout << "iterator::" << __FUNCTION__ << "()\n";
        }
        // operator++ returns boolean indicating end:
        iterator& operator++() {
            cout << "iterator::" << __FUNCTION__ << "()\n";
            if(p)
                p = p->next;
            return *this;
        }
        iterator& operator++(int) {
            cout << "iterator::" << __FUNCTION__ << "(int)\n";
            return operator++();
        }
        // Pointer dereference operator:
        T* operator->() const {
            cout << "iterator::" << __FUNCTION__ << "\n";
            assert(p);
            return &(p->data);
        }
        T& operator*() const {
            cout << "iterator::" << __FUNCTION__ << "\n";
            assert(p);
            return p->data;
        }
        // bool conversion for conditional test:
        operator bool() const {
            cout << "iterator::" << __FUNCTION__ << "\n";
            return bool(p);
        }
        // Comparison to test for end:
        bool operator==(const iterator&it) const {
            cout << "iterator::" << __FUNCTION__ << "\n";
            return p == it.p;
        }
        bool operator!=(const iterator&it) const {
            cout << "iterator::" << __FUNCTION__ << "\n";
            return p != it.p;
        }
    };
    iterator begin() const {
        cout << "Stack::" << __FUNCTION__ << "\n";
        return iterator(*this);
    }
    iterator end() const {
        cout << "Stack::" << __FUNCTION__ << "\n";
        return iterator();
    }
};
template<class T>
Stack<T>::~Stack() {
    cout << "Stack::" << __FUNCTION__ << "\n";
    while(head)
        pop();
}
template<class T>
T Stack<T>::pop() {
    cout << "Stack::" << __FUNCTION__ << "\n";
    if(head == 0) return T();
    T result = head->data;
    Link* oldHead = head;
    head = head->next;
    delete oldHead;
    return result;
}
int main() {
    Stack<TestType> textlines;
    textlines.push(TestType(string("I")));
    textlines.push(TestType(string("love")));
    textlines.push(TestType(string("you")));
    // Use iterator to print lines from the list:
    for(auto it = textlines.begin(); it != textlines.end(); it++){
    //for(auto it = textlines.begin(); it; it++){
        cout << it->word << endl;
        cout << (*it).word << endl;
    }
    return 0;
}