向量迭代器在从向量中擦除时不兼容 [英] vector iterators incompatible while erase from vector

查看:259
本文介绍了向量迭代器在从向量中擦除时不兼容的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个地图,哪些元素是向量。我必须从这些向量中删除所有等于特殊号码的元素 num

  std :: map< size_t,std :: vector< size_t> > MYMAP; (std :: map< size_t,std :: vector< size_t> :: iterator itMap = myMap.begin(); itMap!= myMap.end(); ++ itMap)
{
for(std :: vector< size_t> :: iterator itVec = itMap-> second.begin(); itVec!= itMap-> second.end();)
{
auto itNextVec = itVec;
++ itNextVec;
if(* itVec == num)
{
itMap-> second.erase(itVec);
}
itVec = itNextVec;
}
}

代码导致运行时exepssion。在VS - 矢量迭代器不兼容
有人可以指出原因是什么?



谢谢

解决方案

std :: vector :: erase iterator 返回到列表的下一个位置,所以当你做一个擦除你应该使你的迭代器等于返回的值。



唯一需要考虑的是,返回的迭代器可能是结束,所以你应该检查。



我个人喜欢做的是在擦除后,我得到接下来的迭代器位置,我返回到返回的迭代器的上一个位置,并且在循环中调用一个继续



示例:

  #include< vector> 
#include< iostream>

int main()
{
std :: vector< int>敏;
myInt.push_back(1); myInt.push_back(2); myInt.push_back(3);

for(auto iter = myInt.begin();
iter!= myInt.end();
++ iter)
{
if (* iter == 1)
{
iter = myInt.erase(iter);
if(iter!= myInt.begin())
{
iter = std :: prev(iter);
继续;
}
}

std :: cout<<< * iter<<的std :: ENDL;
}
}

但是在迭代器循环内部进行擦除是皱眉的因为它使旧的迭代器无效,如果你没有计划,可能会导致很多问题。


I have a map which elements are vectors.I have to delete from these vectors all elements which are equal to special number num

std::map<size_t,std::vector<size_t> > myMap;
for (std::map<size_t,std::vector<size_t> >::iterator itMap = myMap.begin();itMap != myMap.end();++itMap )
{
    for (std::vector<size_t>::iterator itVec = itMap->second.begin();itVec != itMap->second.end();)
    {
        auto itNextVec = itVec;
        ++itNextVec;
        if (*itVec == num)
        {
            itMap->second.erase(itVec );
        }
        itVec = itNextVec;
    }
}

The code causes run-time exepssion .In VS - vector iterators incompatible. Can someone point what is the cause for that?

Thanks

解决方案

std::vector::erase returns an iterator to the next position of the list, and so when you do an erase you should make your iterator equal to the returned value.

The only thing that you have to consider is that the returned iterator could be the end so you should check for that.

What I personally like to do is is after doing in an erase and I get the next iterator position, I go back to the previous position of the returned iterator and than call a continue on the for loop

Example:

#include <vector>
#include <iostream>

int main()
{
    std::vector<int> myInt;
    myInt.push_back(1);myInt.push_back(2);myInt.push_back(3);

    for(auto iter = myInt.begin();
        iter != myInt.end();
        ++iter)
    {
        if(*iter == 1)
        {
            iter = myInt.erase(iter);
            if(iter != myInt.begin())
            {
                iter = std::prev(iter);
                continue;
            }
        }

        std::cout << *iter << std::endl;
    }
}

But doing an erase inside of a iterator loop is frowned upon because it invalidates the old iterator and that could cause a lot of issues if you didn't plan for them.

这篇关于向量迭代器在从向量中擦除时不兼容的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆