插入和删除后使用向量迭代器时出错

时间:2015-07-27 17:53:45

标签: c++

我试图在C++中使用向量。我试图在指定的位置使用迭代器插入一个元素,然后使用iterator.But再次删除一些元素。当我为这两个操作使用相同的迭代器时我得到错误。这是我的代码 -

#include <iostream>
#include <vector>
#include <cctype>
using namespace std;
int main()
{
    vector <int> A(10);

    for (int i=0;i<A.size();i++)
    {
        A[i]=i+1;
    }
    vector<int>::iterator p=A.begin();
    p+=2;

    A.insert(p,1,55);

    A.erase(p,p+2);
    for (int i=0;i<A.size();i++)
    {
        cout << A[i] <<"\n";
    }   
    return 0;
}

这给了我以下输出:

*** Error in `./temp': double free or corruption (out): 0x00000000017d4040 ***
55
3
4
5
6
7
8
9
10
Aborted (core dumped)

如果我在A.erase之前添加以下两行,我会得到正确答案。

p=A.begin();
p+=2;
A.erase(p,p+2);

因此,如果p仍指向同一元素,因为其值尚未更改,为什么我需要再次设置p的值。

2 个答案:

答案 0 :(得分:3)

std::vector插入/删除后,所有现有迭代器都无效,不应使用(使用它们会导致未定义的行为)

请记住,向量包含的更改项可能会导致内存分配等,因此旧的迭代器可以指向释放的内存(如指针)

所以当你添加你提到的行并重新初始化迭代器时 - 一切都很好。但在insert现有p不再有效后。

http://en.cppreference.com/w/cpp/container/vector/erasehttp://en.cppreference.com/w/cpp/container/vector/insert中查看有关“迭代器失效”的段落。

您可以考虑添加对reserve的调用,以确保insert上没有重新分配,但在我看来,此类代码仍然容易出错且难以维护。

答案 1 :(得分:1)

根据标准(n4296 C ++ 14)[23.3.6.5/1],向量的插入操作使迭代器无效 - 但并非总是如此:

  

备注:如果新大小大于旧容量,则会导致重新分配。如果没有重新分配,   插入点之前的所有迭代器和引用都保持有效。

和擦除[23.3.6.5/3]

  

效果:在擦除点处或之后使迭代器和引用无效。

这些是规则,你看到正确的行为实际上是UB(未定义的行为) - 这意味着即使在99%的时间内它也可能看起来有效。它还取决于编译器中的实现。