I was wondering how the property maps are implemented in a boost Graph. For example,
I have vertex and edge properties defined like this:
//vertex property:-->
struct NodeInfo { int a , b , c; }; //actual bundled property
struct NodeInfoPropertyTag { // tag and kind (as in boost documentation)
typedef boost::vertex_property_tag kind;
static std::size_t const num;
};
std::size_t const NodeInfoPropertyTag::num = (std::size_t) &NodeInfoPropertyTag::num;
//typedef the Vertex Property
typedef boost::property <NodeInfoPropertyTag, NodeInfo> NodeProperty;
//Similar fashion for Edge Property --> some property for each edge of graph.
typedef boost::property <EdgeInfoPropertyTag, EdgeInfo> EdgeProperty;
My graph is typedef'd as below:
typedef boost::adjacency_list <vecS, vecS, undirectedS, NodeProperty, EdgeProperty, no_property, listS> Graph_t;
Now, while initializing the graph G using above typedef, I can assign properties to vertices and edges with the properties
for eg:
Graph_t G;
typedef graph_traits<Graph_t>::vertex_descriptor vd_t;
// edge_descriptor ed_t;
NodeInfo ninfo1, ninfo2; //put some values in ninfo
vd_t v = add_vertex (ninfo1, G) //add a vertex in G with property ninfo1
vd_t u = add_vertex (ninfo2, G) //add a vertex in G with property ninfo2
EdgeInfo einfo; //initialize edgeinfo for edge property
add_edge (u, v, einfo, G ) edge (u, v) with property einfo is added in G
To access node property of any vertex I can use the any of the 2 methods as follows:
//method 1: direct method: using Tags
// for a vertex "v" --> get()
NodInfo info = boost::get (NodeInfoPropertyTag(), G, v) //get v's property
//modify info
//put the modified property
put (NodeInfoPropertyTag(), G, v, info) // (put in G, key = v, value = info )
//method 2 : using property maps.
//Edge Map and Node Map
typedef typename boost::property_map <Graph_t, EdgeInfoPropertyTag>::type EdgeMap;
typedef typename boost::property_map <Graph_t, NodeInfoPropertyTag>::type NodeMap;
//edge e --> get
EdgeInfo einfo = boost::get (EdgeMap, e)
//modify einfo
//put
put (EdgeMap, e, einfo) //put in the EdgeMap key = e, value = einfo
Now, both the operations are essentially same: i.e. using
//former is translated to the latter -->
get(NodeInfoPropertyTag(), G, "key") is equivalent to get (NodeMap, "key")
My question is:
- how are these properties are stored in the Graph object.
- Is it stored in a map such as std::map<> ? or some list ? or some efficient map-like data structure.
- If so, how can I modify the underlying data structure to std::unordered_map or even concurrent_hashmap or boost::vector_property_map ?
Note: I am not sure I could use vector_prop_map (here) but I would really like to use it so that the vertex id becomes the vector index and more efficient --> it could cause problem in edges though
My graph would contain a million vertices and many many edges, in this way searching in the std::map<> would still be log(n) as such but I want the portability to change the underlying data structure so that I can use unordered_map / concurrent_hashmap
I need concurrent_hashmap (from Intel TBB) because I would be parallelizing my algorithm and so would desire concurrent access the to the property map which is going to be modified by threads.
Please suggest whether is it possible to control and modify such underlying data structures in boost graph for storing edge and vertex properties.