STL列表擦除项目

时间:2010-10-05 18:34:51

标签: c++ stl

  

可能重复:
  Can you remove elements from a std::list while iterating through it?

我希望在迭代时从列表中删除项目。我以前做过这个,但不知怎的,这个简单的例子让我失望了。 thnx提前帮助!

#include<iostream>
#include<list>
using namespace std;

void main()
{
    list<int> x;
    for ( int i =0;i<10; i++)
        x.push_back(i);

    for( list<int>::iterator k = x.begin(); k != x.end();k++)
        cout<<*k<<" ";

    cout<<endl;

    for( list<int>::iterator k = x.begin(); k != x.end();k++)
    {
        if ((*k)%2)
        {
            x.erase(k);
        }
    }

    cout<<endl;
    getchar();
}

4 个答案:

答案 0 :(得分:8)

只是FWIW,您所谈论的内容也可以用(例如)std::list::remove_if完成:

template <class T>
class odd { 
    bool operator()(T const &value) { 
        return value % 2 != 0;
    }

};

// ...
x.remove_if(odd);

使用C ++ 0x和/或Boost lambda,您可以在不单独定义even的情况下执行此操作,这对于像这样的琐碎条件非常方便。理论上你也可以用std :: bind1st,std :: bind2nd,std :: equal和std :: modulus的组合来定义它,但是(IMO)结果将很难破译它会是不可取的。

请注意,std::list::remove_if(与std::remove_if不同)实际上会删除您要求删除的项目,而std::remove_if通常需要与对erase的调用相结合才能实际删除删除已删除的项目。

答案 1 :(得分:5)

erase返回已删除元素后的元素:http://www.cplusplus.com/reference/stl/vector/erase/

所以尝试这样的事情:

for( list<int>::iterator k = x.begin(); k != x.end();)
  if( (*k)%2 )        
    k=x.erase(k);
  else
    ++k;

答案 2 :(得分:3)

不是为(;;)循环编写另一个循环来迭代STL容器,而是使用STL算法和lambda表达式来完成整个过程。

您的示例代码可以重写为:

list<int> x;

int i = 0;
generate_n(back_inserter(x), 10, [&i](){ return i++; });

copy(x.begin(), x.end(), ostream_iterator<int>(cout, " "));
cout << endl;

x.remove_if([](int n){ return n%2==0; });

答案 3 :(得分:0)

执行此操作时,您的迭代器无效。做

k = x.erase(k);