Currently, I have a graph, that I keep tracking of vertices
and labels
by means of an external map
. So anytime I need to access the label property, I find the label in the map and get the mapped vertex
.
/// vertex properties
struct VertexData
{
std::string label;
int num;
};
/// edges properties
struct EdgeData
{
std::string edge_name;
double edge_confidence;
};
/// define the boost-graph
typedef boost::adjacency_list<boost::vecS, boost::vecS,
boost::bidirectionalS,
boost::property<boost::edge_index_t , size_t , VertexData>,
boost::property<boost::edge_weight_t, double, EdgeData> > Graph;
/// define vertexMap
std::map<std::string, vertex_t> vertexMap;
///loop through the vertices to make the vertexMap here ...
vertexMap.insert(std::pair<std::string, vertex_t> (label, v));
/// find any label in the map and access the corresponding vertex
vertex_t vertex = vertexMap.find(label)->second;
Now my question is:
If I want to make a filtered_graph
from current graph by filtering some labels, how should I do that in the class template
? The examples in the boost graph library are different, and I checked also this post boost graph copy and removing vertex but it's quite different from what I want to do.
Thanks for any help.
Filtering
You need a filtering predicate. You can have multiple for different graph elements. But let's focus on vertices.
What you want is a stateful predicate. The way to do this is usually keeping the state outside the predicate and putting a pointer to that inside the predicate:
Live On Coliru
Prints the unfiltered graph (
g
) first, and then the filtered graph (fg
):Indexing
Not really the question, but you can make maintaining an index slightly more friendly using intrusive containers. If you add a hook to the VertexData:
You can use an intrusive-set:
This means you can add all vertices:
What does this buy you? Not a lot per se. But enabling auto-unlinking, it does buy you that when a vertex is removed, it's automatically removed from the index.
Live On Coliru