如何通过参数传递迭代器,实现原迭代器的位置更新?
解决迭代器传值后原变量不更新的问题
哦,这个问题我太熟了——你遇到的是C++里值传递的经典坑!咱们先搞清楚为啥现在的代码没用:
当你把it传给methodB的时候,C++默认是值传递,也就是会创建一个迭代器的副本给methodB里的myIt。你在methodB里执行myIt++,只是把这个副本往前移了一位,而methodA里的原it完全没被碰过,自然每次调用完都还在begin()位置。
下面给你三种靠谱的解决方案,按需选就行:
方案1:传递迭代器的引用(最推荐)
把methodB的参数改成引用类型,这样函数里操作的就是原迭代器本身,而不是副本。修改后的代码如下:
void methodB(list<int>::iterator& myIt){ // 这里加了&,变成引用 myIt++; } void methodA(){ list<int> * myList=new list<int>(); list<int>::iterator it=myList->begin(); // 很多插入操作... methodB(it); // 直接传it,现在会修改原迭代器 // ...后续it已经指向begin()的下一个位置了 delete myList; // 别忘了释放内存! }
这个方案最直观,代码改动最小,也是C++里处理这类问题的常规做法。
方案2:传递迭代器的指针
如果你习惯用指针操作,也可以把参数改成迭代器的指针,通过解引用来修改原迭代器:
void methodB(list<int>::iterator* myIt){ // 参数是指针 (*myIt)++; // 解引用后再自增 } void methodA(){ list<int> * myList=new list<int>(); list<int>::iterator it=myList->begin(); // 很多插入操作... methodB(&it); // 传it的地址 // ... delete myList; }
这种方式也能达到效果,但相比引用,代码可读性稍差一点,除非有特殊需求,不然优先选引用。
方案3:让methodB返回更新后的迭代器
另一种思路是让methodB处理完后把新的迭代器返回,然后在methodA里把原迭代器赋值为返回值:
list<int>::iterator methodB(list<int>::iterator myIt){ // 返回迭代器类型 myIt++; return myIt; } void methodA(){ list<int> * myList=new list<int>(); list<int>::iterator it=myList->begin(); // 很多插入操作... it = methodB(it); // 把返回的新迭代器赋值给原it // ... delete myList; }
这种方式的好处是更“函数式”,如果需要保留原迭代器的状态(比如同时存着旧位置和新位置),这个方案会更灵活。
额外小提示
你现在用new创建了list,一定要记得用delete释放内存,不然会造成内存泄漏。更优雅的做法是用智能指针,比如std::unique_ptr<list<int>> myList = std::make_unique<list<int>>();,这样不用手动管理内存,超出作用域会自动释放。
内容的提问来源于stack exchange,提问作者Antonio1996
相关产品推荐
相关产品推荐

