STL——迭代器失效

来源:互联网 发布:苹果手机淘宝没有了 编辑:程序博客网 时间:2024/06/04 23:22

迭代器失效:

        指向不再存在的元素的迭代器。无效迭代器的使用未定义,可能会导致严重的运行错误。

        众所周知当使用一个容器的insert或者erase函数通过迭代器插入或删除元素"可能"会导致迭代器失效,因此很多建议都是让我们获取insert或者erase返回的迭代器,以便用重新获取新的有效的迭代器进行正确的操作

迭代器失效的类型了:

  1.由于容器元素整体“迁移”导致存放原容器元素的空间不再有效,从而使得指向原空间的迭代器失效。

  2.由于删除元素使得某些元素次序发生变化使得原本指向某元素的迭代器不再指向希望指向的元素。


如下面代码分析:

void PrintList(list<int> l){list<int>::iterator it = l.begin();//iterator->迭代器while (it != l.end()){if ((*it) % 2 == 0){l.erase(it);}++it;}cout<<endl;}

下面是链表删除时出现的异常——迭代器失效

l.erase(it)正常删除以后,迭代器就失效了,it指向了一个随机值

而后++it,此时的it已经成为了野指针,此时对野指针进行自加操作,自然会引来异常


我们需要接收迭代器当前的位置,重新获取新的有效的迭代器进行正确的操作

方法一:

void PrintList(list<int> l){list<int>::iterator it = l.begin();//iterator->迭代器while (it != l.end()){list<int>::iterator cur = it;//接收it的位置++it;if ((*cur) % 2 == 0){l.erase(cur);//对cur进行删除操作}}cout<<endl;}

方法二:

void PrintList(list<int> l){list<int>::iterator it = l.begin();//iterator->迭代器while (it != l.end()){if ((*it) % 2 == 0){it = l.erase(it);//还是用原来的迭代器记住自己当前的位置} else{++it;}}cout<<endl;}

关于vector中的迭代器失效

void PrintVector(vector<int> v){vector<int>::iterator it = v.begin();//iterator->迭代器while (it != v.end()){if ((*it) % 2 == 0){v.erase(it);}++it;}cout<<endl;}

下面是vector删除时出现的异常——迭代器失效

v.erase(it)正常删除以后,迭代器就失效了,it指向了一个随机值

而后++it,此时的it已经成为了野指针,此时对野指针进行自加操作,自然会引来异常




          解决方法已经不能用上面处理list的erase删除异常的处理方法一来操作了,方法一种指针总是之向下一个位置,而vector中删除当前位置的数据是后面数据的覆盖,指针的偏移会越过数据,出现异常。故不能用方法一。

   这里可以使用方法二来处理

void PrintVector(vector<int> v){vector<int>::iterator it = v.begin();//iterator->迭代器while (it != v.end()){if ((*it) % 2 == 0){it = v.erase(it);//用原来的迭代器记住当前删除的位置}++it;}cout<<endl;}

       今天我才刚刚接触STL,也是第一次知道迭代器失效,所以这里写的很粗糙,如果有描述不当的地方请指出,后续深入学习迭代器后会指出迭代器失效的各种情况以及处理迭代器失效的各种方法。

对于也是刚刚接触迭代器的童鞋们,可以看看我的上一篇博客,里面有对迭代器的初步认识。


0 0
原创粉丝点击