2012-01-04 64 views
0

我想从std::list删除一个元素,然后重新指向这个名单,但是当我做这种方式如何在擦除en元素后正确指向std :: list(double for循环)?

for(std::list<CvRect>::iterator it = listOfCvRects.begin(); it != listOfCvRects.end(); it++) 
{ 
    for(std::list<CvRect>::iterator jt = listOfCvRects.begin(); jt != listOfCvRects.end(); jt++) 
    { 
     if(it == jt) 
     { continue;} 

     if((jt->x) > (it->x) //.. more conditions...) 
     { 
      jt = listOfCvRects.erase(jt); 
      //OR 
      //listOfCvRects.erase(jt++); 
     } 
    } 

} 

我和未处理的异常:iterator is unincrementable

+0

[可能重复(http://stackoverflow.com/q/596162/624900) – jterrace 2012-01-04 23:01:31

+0

如果条件是对称的,你可以在启动内环'jt = it;'。 – 2012-01-04 23:08:15

回答

4

我相信问题是,在在某些情况下(你删除一个元素的情况),你需要双倍递增迭代器。您的循环如下所示:

for(std::list<T>::iterator jt = l.begin(); jt != l.end(); jt++) { 
    .... 
} 

但是这里面你正在做这样的事情:

jt = l.erase(jt); 

所以,如果情况发生,你做擦除,你删除它,并在同时,将迭代器设置为下一个元素......但是,您也可以使用jt++来递增!

简单的方法来固定,这是重新写了for循环稍微适应这种形式的因素:

for(std::list<T>::iterator it = l.begin(); it != l.end();) { // notice no increment! 
    // ... 
    if(cond) { 
     it = l.erase(it); 
    } else { 
     ++it; 
    } 
} 

所以你在做一个或另一个增量,但不可能兼顾。

+0

那么我能做些什么来避免它呢? – Patryk 2012-01-04 23:06:11

+0

@Patryk:看到更新,我试图在输入完整答案时快速获得基本知识:-)。 – 2012-01-04 23:07:42

0

从列表中清除元素会使指向该元素的迭代器失效,但不会指向其他迭代器。因此,你需要擦除之前做增量:

for(std::list<CvRect>::iterator it = listOfCvRects.begin(); it != listOfCvRects.end(); it++) { 
    std::list<CvRect>::iterator jt = listOfCvRects.begin(); 
    while (jt != listOfCvRects.end()) { 
     if(it == jt) continue; 
     if((jt->x) > (it->x) //.. more conditions...) { 
      listOfCvRects.erase(jt++); 
     } else { 
      jt++; 
     } 
    } 
} 
+0

'erase'将迭代器返回到下一个元素(或'end()')。 – 2012-01-04 23:06:35