2011-12-23 9 views
9

Byłem w górę iw dół stackoverflow i nawet bardzo, bardzo miły Dr. Dobbs article, ale nie mogę znaleźć ostatecznej odpowiedzi na to pytanie.Jak usunąć * I KONTYNUUJ * używając std :: reverse_iterator?

Część odpowiedzi na pytanie What are the shortcomings of std::reverse_iterator? mówi, że może to w ogóle nie być możliwe.


std::list::reverse_iterator it = list.rbegin(); 

while( it != list.rend()) 
{ 
    int value=*it; 
    if(some_cond_met_on(value)) 
    {  
     ++it; 
     list.erase(it.base()); 
    } 
    else 
    { 
    ++it; 
    } 
} 

PS: wiem, że istnieją inne alternatywy, takie jak erase_if(), ale szukam odpowiedzi na to konkretne pytanie.

Odpowiedz

15

To powinno być tylko

std::list<int>::reverse_iterator it = list.rbegin(); 

while( it != list.rend()) 
{ 
    int value=*it; 
    if(some_cond_met_on(value)) 
    {  
     ++it; 
     it= reverse_iterator(list.erase(it.base()); // change to this! 
    } 
    else 
    { 
    ++it; 
    } 
} 
+0

dam jej spróbować . Jak wymyśliłeś ten jeden? (Po prostu prosi o naukę) – Migs

+0

@Migs, niezmiennikiem odwrotnych iteratorów jest: '& * (reverse_iterator (i)) == & * (i - 1)'. Odwróć się od tego (lub po prostu pomyśl o usunięciu 'rbegin()') i dojdziesz do kodu w odpowiedzi. – MSN

+0

Dzięki @MSN. Działało idealnie. Czytałem ten niezmiennik w artykule Dobbsa, ale chyba nie mogę pojąć jego implikacji. Będę patrzył, dopóki coś (mam nadzieję) się nie wydarzy. – Migs

0

Większość erase() implementacje widziałem iterator zwróci następny w kolejności dokładnie takiej sytuacji, np:

std::list<int>::reverse_iterator it = list.rbegin(); 
while(it != list.rend()) 
{ 
    int value = *it; 
    if(some_cond_met_on(value)) 
    { 
     it = list.erase(it); 
    } 
    else 
    { 
     ++it; 
    } 
} 
+0

To się zgadza. Jednak wymazywanie jest elementem struktury, a nie iteratorem. W związku z tym, niezależnie od tego, czy używasz iteratora czy reverse_iteratora, funkcja kasowania() nadal akceptuje i zwraca iterator. Nie ma r_erase(), która akceptuje i zwraca reverse_iterator. –