Home > Blockchain >  vector iterator not behaving properly
vector iterator not behaving properly

Time:11-06

I want to iteratively use insert to modify the first element in a vector<int>(I know that with vector it's better to insert element in the back, I was just playing).

    int main() {
        vector<int> v1 = {1,2,2,2,2};
        auto itr = v1.begin();
        print_vector(v1);
        cout<<*itr<<endl; // ok, itr is pointing to first element
        v1.insert(itr,3); 
        cout<<*itr<<endl; // after inserting 3 itr is still pointing to 1
        print_vector(v1); 
        cout<<*itr<<endl; // but now itr is pointing to 3 
        v1.insert(itr,7); 
        print_vector(v1); 
        cout<<*itr<<endl;
        return 0;
    }

v[]: 1 2 2 2 2
1
1
v[]: 3 1 2 2 2 2
3
v[]: 131072 3 1 2 2 2 2

Process finished with exit code 0

So my problem here are mainly 2:

  1. After v1.insert(itr,3), itr is still pointing to 1. After the call of print_vector() now itr is pointing to 3. Why?
  2. Ok now itr its pointing to 3 (the first element of v1). I call v1.insert(itr,7) but instead of placing 7 as the first element, it place 131072. Again, why?

The print_vector function I have implemented is the following:

void print_vector(vector<int> v){
    cout<<"v[]: ";
    for(int i:v){
        cout<<i<<" ";
    }
    cout<<endl;
}
   

CodePudding user response:

After inserting an element to a vector, any of its iterators are invalidated, meaning any behavior involving them falls under undefined behavior. You can find a list of iterator invalidation conditions in the answers on Iterator invalidation rules for C containers.

Anything you're experiencing after the first v1.insert() call falls under undefined behavior, as you can clearly see with the placement of 131072 (an arbitrary value).

If you refresh the iterator after every insertion call, you should get normal behavior:

int main()
{
    vector<int> v1 = { 1,2,2,2,2 };
    auto itr = v1.begin();
    print_vector(v1);
    cout << *itr << endl;

    v1.insert(itr, 3);
    itr = v1.begin(); // Iterator refreshed

    cout << *itr << endl;
    print_vector(v1);
    cout << *itr << endl;

    v1.insert(itr, 7);
    itr = v1.begin(); // Iterator refreshed

    print_vector(v1);
    cout << *itr << endl;

    return 0;
}

And the output:

v[]: 1 2 2 2 2
1
3
v[]: 3 1 2 2 2 2
3
v[]: 7 3 1 2 2 2 2
7
  • Related