【问题标题】:should I keep track of vertex descriptors in boost graph library?我应该跟踪提升图形库中的顶点描述符吗?
【发布时间】:2017-12-20 11:03:17
【问题描述】:

我有一个用以下内容实例化的图表:

typedef boost::property<boost::edge_weight_t, uint32_t> EdgeWeightProperty;
typedef boost::property<boost::vertex_index_t, uint32_t> VertexProperty;
typedef boost::adjacency_list<boost::vecS, boost::setS,
                              boost::undirectedS, VertexProperty,
                              EdgeWeightProperty, boost::setS> Graph;

我需要更新此图表,例如添加或删除边缘。由于我使用集合来存储顶点,所以我不能使用它们的索引,但我可以保留一张地图:

unordered_map<uint32_t, Vertex_Descriptor>

这会将我的索引映射到顶点描述符,因此我以后可以直接在 BGL 中访问,这种方法有效,但会增加此映射开销。

在 BGL 中获取/放置顶点时,我能否以某种方式指定自定义索引或要比较的内容?还是在地图中保留顶点描述符是最好的方法?

coliru 上的完整示例

【问题讨论】:

    标签: c++ boost boost-graph


    【解决方案1】:

    简短回答:是的。

    注意事项:

    1. 考虑一下文档不足的labeled_graph&lt;&gt; 适配器。我相信它在库示例中使用过,我也have a number of answers using it on this site (免责声明:我还发现了一些错误,所以 YMMV)

    2. 你自己的全局 add_vertex 助手没有被使用,即使你写了:

      const auto vd = add_vertex(i, g);
      

      小心 ADL!您将函数命名为 add_vertex,除非您编写 (add_vertex)(i, g),否则 ADL 会在 boost 中找到重载,因为 adjacency_list&lt;&gt; 来自该命名空间(以及其他相关类型)。

      因此,您可以删除您的辅助函数,但仍然使用 boost add_vertex 重载获取属性:MutablePropertyGraph concept, under "Valid Expressions"

      for (int i = 0; i < 10; ++i)
           id_vertex[i] = add_vertex(i, g);
      
    3. 还替换循环以打印您可以使用的图形print_graph

    Live On Coliru

    #include <boost/graph/adjacency_list.hpp>
    #include <boost/graph/graph_utility.hpp>
    #include <iostream>
    
    typedef boost::property<boost::vertex_index_t, uint32_t> VertexProperty;
    typedef boost::property<boost::edge_weight_t, uint32_t> EdgeWeightProperty;
    typedef boost::adjacency_list<boost::vecS, boost::setS, boost::undirectedS, VertexProperty, EdgeWeightProperty,
                                  boost::setS> Graph;
    typedef boost::graph_traits<Graph>::vertex_descriptor Vertex;
    typedef boost::graph_traits<Graph>::vertex_iterator vertex_it;
    
    int main() {
        Graph g;
        std::unordered_map<uint32_t, Vertex> id_vertex;
    
        for (int i = 0; i < 10; ++i)
            id_vertex[i] = add_vertex(i, g);
    
        std::pair<vertex_it, vertex_it> vp;
        for (int i = 0; i < 9; ++i)
            add_edge(id_vertex[i], id_vertex[i + 1], g);
    
        clear_vertex(id_vertex[2], g);
        remove_vertex(id_vertex[2], g);
    
        print_graph(g);
    }
    

    打印

    0 <--> 1 
    1 <--> 0 
    3 <--> 4 
    4 <--> 3 5 
    5 <--> 4 6 
    6 <--> 5 7 
    7 <--> 6 8 
    8 <--> 7 9 
    9 <--> 8 
    

    【讨论】:

    • 感谢您的快速回答!辅助函数是其他代码的残留物。很遗憾我必须将程序的空间增加一倍才能正常工作。人们会期望一种方法来重载顶点 id :(
    • 想法:您不必一直保留外部索引。您还可以使用向量进行更有效的分配。另请参阅有关使用侵入式容器的这些答案:stackoverflow.com/questions/32296206/…stackoverflow.com/questions/45845469/…
    猜你喜欢
    • 1970-01-01
    • 2018-08-22
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-03-05
    • 1970-01-01
    • 2010-09-18
    相关资源
    最近更新 更多