擦除std :: vector,debug,release

时间:2011-12-06 04:16:56

标签: c++ debugging vector release

std::vector<int> va; //和push_back 1~100

std::vector<int>::iterator i = va.begin();
for(i; i != va.end(); )
{
    if((*i) == 5) va.erase(i);
    else i++
}

调试运行时,此代码100%崩溃。

但是在发布运行时不要崩溃这段代码。

为什么会这样?

此代码中有哪些不同的调试和发布模式?

3 个答案:

答案 0 :(得分:2)

您有未定义的行为,因为您使用的是无效的迭代器(i使erase()失效)。

使用Erase-remove Idiom

避免整个问题
va.erase(std::remove(va.begin(), va.end(), 5), va.end());

答案 1 :(得分:1)

vector::erase返回一个新的迭代器,因为它使当前的迭代器无效。

if((*i) == 5) va.erase(i);

应该是

if((*i) == 5) i = va.erase(i);

答案 2 :(得分:1)

正如其他人所指出的,崩溃是由于您在调用va.erase()后继续使用的无效迭代器。

现在,关于它在Release模式下工作的原因,在某些情况下,Release模式下std::vector<>的迭代器是一个指向动态分配数组的简单指针。当您调用erase时,迭代器继续指向数组的同一元素,而数组的内容已被erase函数移动。这是未定义的行为和标准库实现特定的,但非常常见。 在任何情况下都不应该依赖便携式代码中的行为。

但是,在某些标准库实现中,调试模式迭代器执行检查并且比简单指针更复杂。因此,他们可以检测到您正在做一些不合法的事情并故意导致崩溃,以便您可以识别您的错误。