Agrudge Amicus
Agrudge Amicus

Reputation: 1103

Vector insert within the same object

I was trying to insert few values from a vector to that same vector object but it seems to have erred:

#include<iostream>
#include<vector>

using namespace std;

int main()
{
    vector<int> vec;
    for(int i=0;i<9;i++)
    {
        vec.push_back(i+1);
    }

    vec.insert(vec.begin(),vec.begin()+2,vec.end()-4);  //PROBLEM
    vector<int>::iterator ivec=vec.begin();
    while(ivec!=vec.end())
    {
        cout<<*ivec<<' ';
        ++ivec;
    }
    cout<<endl;
    return 0;
}

I am expecting that elements from vec.begin()+2 i.e. 3 to element vec.end()-4 i.e. 6 are inserted in the vector. But the output is:

3 1 2 1 2 3 4 5 6 7 8 9

Compiler is g++ 4.1.2. Where am I wrong in this?

Upvotes: 4

Views: 606

Answers (2)

john
john

Reputation: 87959

The problem is that when you start inserting elements you invalidate any existing iterators to that vector, including the iterators that specify the range you are trying to insert. Simple solution is to copy the slice of the vector you want to insert first.

 vector<int> tmp(vec.begin() + 2, vec.end() - 4);
 vec.insert(vec.begin(), tmp.begin(), tmp.end());

Upvotes: 9

L. F.
L. F.

Reputation: 20579

vec.insert(vec.begin(),vec.begin()+2,vec.end()-4);

Here, you pass to insert the iterators to the container itself. This is not allowed because of iterator invalidation.

Per [tab:container.req.seq]:

 a.insert(p,i,j)

Expects: T is Cpp17EmplaceConstructible into X from *i. For vector and deque, T is also Cpp17MoveInsertable into X, Cpp17MoveConstructible, Cpp17MoveAssignable, and swappable ([swappable.requirements]). Neither i nor j are iterators into a.

Effects: Inserts copies of elements in [i, j) before p. Each iterator in the range [i, j) shall be dereferenced exactly once.

Therefore, the behavior is undefined.

Upvotes: 4

Related Questions