Prev: comparing iterators
Next: How to convert C to C++?
From: restor on 19 Dec 2009 15:06 Hi, I need to perform a remove_if algorithm on a boost::ptr_vector. I am using boost::ptr_vector to store types that have no copy or clone operation. std::remove_if doesn't work due to the lack of copy/clone operations. So I wrote my own function. It is possible to write it in many ways, but any solution I can think of is worse than the one that is using a goto statement. ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ typedef boost::ptr_vector<NonCopyable> VecT; typedef boost::function<bool(NonCopyable const&)> FunT; void removeIf( VecT & list, FunT fun ) { NEXT_DELETION_TARGET_ITERATION: BOOST_AUTO( it, list.begin() ); BOOST_AUTO( end, list.end() ); for( ; it != end ; ++it ) { if( fun(*it) ) { list.release( it ); goto NEXT_DELETION_TARGET_ITERATION; } } } ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ In addition, I am using a VC++ 2005 compiler that automatically checks iterator invelidation, and crashes in runtime for some solutions that appeared correct to me. I am not sure if I just have a bad day, or if it is a situation that just needs a goto. Can anyone think of a solution that doesn't use goto, but doesn't perform redundant checks or repeat instructions? Regards, &rzej -- [ See http://www.gotw.ca/resources/clcm.htm for info about ] [ comp.lang.c++.moderated. First time posters: Do this! ]
From: Bo Persson on 19 Dec 2009 21:48 restor wrote: > Hi, > I need to perform a remove_if algorithm on a boost::ptr_vector. I am > using boost::ptr_vector to store types that have no copy or clone > operation. std::remove_if doesn't work due to the lack of copy/clone > operations. So I wrote my own function. It is possible to write it > in many ways, but any solution I can think of is worse than the one > that is using a goto statement. > > ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ > > typedef boost::ptr_vector<NonCopyable> VecT; > typedef boost::function<bool(NonCopyable const&)> FunT; > > void removeIf( VecT & list, FunT fun ) > { > NEXT_DELETION_TARGET_ITERATION: > > BOOST_AUTO( it, list.begin() ); > BOOST_AUTO( end, list.end() ); > > for( ; it != end ; ++it ) { > if( fun(*it) ) { > list.release( it ); > goto NEXT_DELETION_TARGET_ITERATION; > } > } > } > > ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ > > In addition, I am using a VC++ 2005 compiler that automatically > checks iterator invelidation, and crashes in runtime for some > solutions that appeared correct to me. > I am not sure if I just have a bad day, or if it is a situation that > just needs a goto. > Can anyone think of a solution that doesn't use goto, but doesn't > perform redundant checks or repeat instructions? > It could be that you have found a use for goto. It seems to happen about once every 10 years, or so. Otherwise I would have expected list.release to return the next iterator it = list.release(it); or that you could increment the iterator before releasing the node list.release(it++); Bo Persson -- [ See http://www.gotw.ca/resources/clcm.htm for info about ] [ comp.lang.c++.moderated. First time posters: Do this! ]
From: restor on 20 Dec 2009 11:01 > ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ > > typedef boost::ptr_vector<NonCopyable> VecT; > typedef boost::function<bool(NonCopyable const&)> FunT; > > void removeIf( VecT & list, FunT fun ) > { > NEXT_DELETION_TARGET_ITERATION: > > BOOST_AUTO( it, list.begin() ); > BOOST_AUTO( end, list.end() ); > > for( ; it != end ; ++it ) { > if( fun(*it) ) { > list.release( it ); > goto NEXT_DELETION_TARGET_ITERATION; > } > } > } > > ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ > > In addition, I am using a VC++ 2005 compiler that automatically checks > iterator invelidation, and crashes in runtime for some solutions that > appeared correct to me. > I am not sure if I just have a bad day, or if it is a situation that > just needs a goto. > Can anyone think of a solution that doesn't use goto, but doesn't > perform redundant checks or repeat instructions? It looks like I did have a bad day. A simple code: void removeIf( VecT & list, FunT fun ) { list.erease_if( fun ); } does just it. Regards, &rzej -- [ See http://www.gotw.ca/resources/clcm.htm for info about ] [ comp.lang.c++.moderated. First time posters: Do this! ]
|
Pages: 1 Prev: comparing iterators Next: How to convert C to C++? |