|
Boost Users : |
Subject: Re: [Boost-users] [BGL] adjacency_iterator invalidation with adjacency_list<listS, listS, unorderedS>
From: cobalto (scott.a.merritt_at_[hidden])
Date: 2010-02-23 13:21:01
cobalto wrote:
>
> According to
> http://www.boost.org/doc/libs/1_39_0/libs/graph/doc/adjacency_list.html,
> adjacency_iterators into adjacency_list<listS, listS, unorderedS, ... >
> graphs should not be invalidated by
> calls to clear_vertex() and remove_vertex().
>
> However, running the below code results in iterator invalidation directly
> following the call to clear_vertex()
> From most likely to least likely, am I 1) doing something wrong,
> 2)misreading something in the documentation, or 3) encountering a bug?
>
> using namespace boost;
> typedef property<vertex_name_t, unsigned short> usVertName;
> typedef boost::adjacency_list< listS, listS, undirectedS, usVertName >
> Graph;
> typedef boost::graph_traits<Graph>::vertex_descriptor Vertex;
>
> void RemoveVertAndNeighbors(Vertex v, Graph& g)
> {
> typedef boost::graph_traits<Graph>::adjacency_iterator AdjVertIt;
> AdjVertIt avi, avinext, av_end;
> tie(avi, av_end)=adjacent_vertices(v,g);
> for (avinext=avi; avi != av_end; avi=avinext)
> {
> ++avinext;
> //avinext is a valid iterator here
> clear_vertex(*avi,g); //Should Invalidate Edge Iterators and Edge
> Refs that touch Vertex *avi
> //******ERROR: avinext appears invalid*******//
> //either no longer points to the same element or otherwise crashes
> the program
> remove_vertex(*avi,g); //Should Invalidate avi and any other Vertex
> Reference pointing to *avi
> //But should not affect avinext
> }
> remove_vertex(v,g);
> }
>
> Any Help is greatly Appreciated
>
More Info:
a 2-pass method where I make a std::list of vertex descriptors and then
process these vertices works.
This means vertex descriptors are not being invalidated, but
adjacency_iterators are.
Substituting the following code in the above example avoids the run-time
error :
void RemoveVertAndNeighbors( Vertex v, Graph &g)
{
typedef boost::graph_traits<Graph>::adjacency_iterator AdjVertIt;
std::list<Vertex> vl;
AdjVertIt avi, av_end;
for (tie(avi, av_end) = adjacent_vertices(v, g); avi != av_end; ++avi)
vl.push_back(*avi);
for (std::list<Vertex>::iterator it = vl.begin(); it != vl.end(); ++it
{
clear_vertex((*it), g);
remove_vertex((*it), g);
}
remove_vertex(v,g);
return true;
}
I'm wondering if the documentation is incorrect. Perhaps it is just
imprecise, and removing any edge from the source vertex of an
adjacency_iterator invalidates that iterator?
Anyone with additional insight would be very helpful.
-- View this message in context: http://old.nabble.com/-BGL--adjacency_iterator-invalidation-with-adjacency_list%3ClistS%2C-listS%2C-unorderedS%3E-tp27647214p27707861.html Sent from the Boost - Users mailing list archive at Nabble.com.
Boost-users list run by williamkempf at hotmail.com, kalb at libertysoft.com, bjorn.karlsson at readsoft.com, gregod at cs.rpi.edu, wekempf at cox.net