c++ - 迭代 vector 并删除

标签 c++

对于许多人来说,很明显这段代码会产生段错误。

#include <iostream>
#include <string>
#include <vector>

int main()
{
    std::vector<int> ints;
    ints.push_back(5);
    std::vector<int>::iterator it;
    for(it = ints.begin(); it != ints.end(); ++it){
        std::cout << *it;
        it = ints.erase(it);
    }
}

如果我们删除++it并添加一个删除条件,我们就可以避免这个错误。但问题的真正原因是什么?在我们的循环中,我们说,对于迭代器的开始,直到它到达末尾,递增一,打印出值,然后删除它。是因为在这种情况下,我们已经删除了下一个(唯一的)值,所以在“结束”时调用了++it 吗?

最佳答案

Is it because the ++it is called at the "end" when, in this condition, we've already removed the next (only) value?

是的。

std::erase 返回一个指向被删除元素之后的元素的迭代器。

考虑一个只有一个元素的 vector ,那么你的循环基本上是:

it = ints.begin(); 
std::cout << *it;
it = ints.erase(it);    // it == ints.end()
++it;                   // boom
//if (it != ints.end()) // more boom

请参见此处:Is it allowed to increment an end iterator? - 没有。

此类问题是更喜欢使用删除删除惯用语而不是手写循环来删除元素的原因之一。

关于c++ - 迭代 vector 并删除,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60399074/

相关文章:

c++ - 对 `atexit' 的 undefined reference

c++ - 在 C++ 中创建带有结构的节点时出现段错误

c++ - 为什么boost mpl set允许非唯一类型

c++ - 为什么 EndScene Hook 需要参数?

c++ - Qt QML MenuBar 和菜单不显示

c++ - 这两种动态扩展数组的方法有什么区别?

C++ 17 std::filesystem 无法在其他(Windows 10)计算机上运行

c++ - 具有私有(private)成员的结构的构造函数

c++ - opencv中灰度图像的熵

c++ - 使用getline时如何检测文件结尾?