Jump to content
  • Advertisement
Sign in to follow this  
Gink

iterator & list runtime errors

This topic is 4888 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

int ia[] = { 0, 1, 1, 2, 3, 5, 8, 13, 21, 55, 89 }; list<int> ilist( ia, ia+11 ); for(list<int>::iterator i = ilist.begin() ; i != ilist.end(); i++){ if((*i)%2 != 0){ ilist.erase(i); } } this code generates errors for some reason, i thought to delete an item from a list you supply an iterator position. If i take out erase it works, but isnt that the right syntax?

Share this post


Link to post
Share on other sites
Advertisement
when you erase, your iterator gets invalidated, you need to make use of the return value of erase()

Share this post


Link to post
Share on other sites

int ia[] = { 0, 1, 1, 2, 3, 5, 8, 13, 21, 55, 89 };
list<int> ilist( ia, ia+11 );
for(list<int>::iterator i = ilist.begin(); i != ilist.end(); i++){
if((*i)%2 != 0){
i = ilist.erase(i);
}
}


it works now, but the output is wrong. Its supposed to delete all odd numbers but it only works on half of them it seems.

Share this post


Link to post
Share on other sites
You should read up on how the erase function works...you were iterating when you shouldn't have. Take a look at this...

#include <iostream>
#include <list>
using std::cout;
using std::endl;
using std::list;


int main(int argc, char **argv)
{
argc, argv;

int ia[] = { 0, 1, 1, 2, 3, 5, 8, 13, 21, 55, 89 };
list<int> ilist( ia, ia+11 );


list<int>::iterator i = ilist.begin();
while( i != ilist.end() )
{
if( 0 != ( (*i) % 2) )
{
i = ilist.erase(i);
// only increment when you aren't deleting....
}
else
{
i++;
}
}

// print the result out...
for( i = ilist.begin(); i != ilist.end(); ++i )
cout << (*i) << endl;

return(0);

}


Share this post


Link to post
Share on other sites
Quote:
Original post by moeron
You should read up on how the erase function works...you were iterating when you shouldn't have. Take a look at this...
*** Source Snippet Removed ***


i tried finding documentation on it and all I found was it returns an iterator. I assume the erase method returns an iterator pointing to the next iterator?

Share this post


Link to post
Share on other sites
Quote:
Original post by Gink
i tried finding documentation on it and all I found was it returns an iterator. I assume the erase method returns an iterator pointing to the next iterator?


Yep, so you were doubling up. MSDN usually has some in depth information about stuff like this.

EDIT:
Here is something I just found by searching MSDN for list::erase
Quote:
MSDN list::erase Info
list::erase

iterator erase(iterator it);
iterator erase(iterator first, iterator last);

The first member function removes the element of the controlled sequence pointed to by it. The second member function removes the elements of the controlled sequence in the range [first, last). Both return an iterator that designates the first element remaining beyond any elements removed, or end() if no such element exists.

Erasing N elements causes N destructor calls. No reallocation occurs, so iterators and references become invalid only for the erased elements.

Share this post


Link to post
Share on other sites
It returns an iterator pointing to the next node after the erased one. Now, if you think about it, this is pretty much the same as incrementing the iterator. Because you already increment it at the end of every round of the for loop, it basically gets incremented twice each time a node is erased. That's why you must only increment the iterator manually if a node wasn't erased.

Share this post


Link to post
Share on other sites
Quote:
Original post by Gink
Its supposed to delete all odd numbers but it only works on half of them it seems.



#include <cstddef> // size_t
#include <algorithm> // copy
#include <iterator> // ostream_iterator
#include <list>
#include <iostream>

bool is_odd(int val) {
return ((val % 2) != 0);
}

int main() {

int ia[] = { 0, 1, 1, 2, 3, 5, 8, 13, 21, 55, 89 };
const std::size_t N = sizeof(ia) / sizeof(int);

std::list<int> ilist(ia, ia + N);

std::cout << "before:\n";

std::copy(ilist.begin(), ilist.end(),
std::ostream_iterator<int>(std::cout, "\n"));

ilist.remove_if(is_odd);

std::cout << "\nafter:\n";

std::copy(ilist.begin(), ilist.end(),
std::ostream_iterator<int>(std::cout, "\n"));

}


remove/remove_if removes all occurrences of some given criteria/value. In general try to avoid explicit hand-written loop code in favour of using the standard library generic algorithms

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!