I've read a few posts concerning iterator invalidation, and it seems that inserts that require a vector reallocation would invalidate iterators. Also shouldn't erases in the middle of the vector cause an invalidation?
I don't have a clear understanding of this, not sure why using these iterators after resizes and erases from begin, middle, and end doesn't break them:
#include <cstdlib>
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
int main(int argc, char** argv) {
    vector<int> v;
    v.reserve(10);
    for (int i = 0; i < 10; i++)
        v.push_back(i);
    for (auto x = v.begin(); x != v.end(); x++) {
        cout << *x << endl;
    }
    cout << endl << "RESIZE" << endl << endl;
    for (int i = 10; i < 20; i++)
        v.push_back(i);
    for (auto x = v.begin(); x != v.end(); x++) {
        cout << *x << endl;
    }
    cout << endl << "RESIZE 2" << endl << endl;
    for (int i = 20; i < 200; i++)
        v.push_back(i);
    for (auto x = v.begin(); x != v.end(); x++) {
        cout << *x << endl;
    }
    cout << endl << "REMOVES" << endl << endl;
    v.erase(v.begin());
    v.pop_back();
    v.erase(v.begin() + 17);
    for (auto x = v.begin(); x != v.end(); x++) {
        cout << *x << endl;
    }
    return 0;
}
 
     
    