【问题标题】:Find all reachable vertices in a Boost BGL graph using BFS使用 BFS 在 Boost BGL 图中查找所有可到达的顶点
【发布时间】:2019-05-20 23:17:48
【问题描述】:

我已经构建了一个 boost BGL 图:

using vertex_t = std::variant<node_t, specialNode_t>; // structs
using edge_t = std::variant<TerminalType>;            // enum

using Graph_t = boost::adjacency_list<
    boost::vecS,
    boost::vecS,
    boost::undirectedS,
    vertex_t,
    edge_t>;

Graph_t myGraph;

我正在尝试查找(收集)从某个起点(顶点)可到达的所有顶点(按它们的距离排序)。这意味着我想创建一个从某个起始顶点可到达的所有顶点的列表,其中“更近”的顶点存储在列表/向量的早期。因此我(认为我)需要 BFS。

不幸的是,我没能找到如何在没有编译错误的情况下做到这一点:

boost::queue<vertex_t> Q;
boost::default_bfs_visitor vis; // Will do my collecting visitor later...

auto indexmap = boost::get(boost::vertex_index, myGraph);
auto colormap = boost::make_vector_property_map<boost::default_color_type>(indexmap);

boost::breadth_first_visit(myGraph, start, std::ref(Q), vis, colormap);

这会导致以下错误:

Error   C2039   'push': is not a member of 'std::reference_wrapper<boost::queue<ListSim::vertex_t,std::deque<_Tp,std::allocator<_Ty>>>>'
Error   C2039   'empty': is not a member of 'std::reference_wrapper<boost::queue<ListSim::vertex_t,std::deque<_Tp,std::allocator<_Ty>>>>'
Error   C2039   'top': is not a member of 'std::reference_wrapper<boost::queue<ListSim::vertex_t,std::deque<_Tp,std::allocator<_Ty>>>>'
Error   C2039   'pop': is not a member of 'std::reference_wrapper<boost::queue<ListSim::vertex_t,std::deque<_Tp,std::allocator<_Ty>>>>'
Error   C2039   'push': is not a member of 'std::reference_wrapper<boost::queue<ListSim::vertex_t,std::deque<_Tp,std::allocator<_Ty>>>>'

我的问题:

  1. 谁能解释我的错误?或者也许是一个指向 例子?
  2. 是否有更好的(就效率而言)或不同的方法来实现该目标?

(我虽然先使用“connected_components”...但它使用的 DFS 无法满足我的距离/排序标准)。

【问题讨论】:

    标签: c++ boost graph boost-graph


    【解决方案1】:

    文档说缓冲区需要是vertex_descriptors 的队列。您不小心将其声明为具有 vertex_t(顶点属性包)作为值类型。

    修复它:

    using vertex_descriptor = boost::graph_traits<Graph_t>::vertex_descriptor;
    
    boost::queue<vertex_descriptor> Q;
    

    然后编译:

    Live On Coliru

    #include <boost/graph/adjacency_list.hpp>
    #include <boost/graph/breadth_first_search.hpp>
    #include <variant>
    #include <queue>
    
    struct node_t {
    };
    struct specialNode_t {
    };
    enum class TerminalType {
    };
    
    using vertex_t = std::variant<node_t, specialNode_t>; // structs
    using edge_t = std::variant<TerminalType>;            // enum
    
    using Graph_t = boost::adjacency_list<boost::vecS, boost::vecS, boost::undirectedS, vertex_t, edge_t>;
    
    int main() {
        Graph_t myGraph(5);
        boost::default_bfs_visitor vis; // Will do my collecting visitor later...
    
        auto indexmap = boost::get(boost::vertex_index, myGraph);
        auto colormap = boost::make_vector_property_map<boost::default_color_type>(indexmap);
    
        using vertex_descriptor = boost::graph_traits<Graph_t>::vertex_descriptor;
    
        boost::queue<vertex_descriptor> Q;
        boost::breadth_first_visit(myGraph, 0, Q, vis, colormap);
    }
    

    【讨论】:

    • 谢谢。我还必须用 Q 替换 std::ref(Q) ......一行中有两个错误。天哪
    • 没什么 :) 这是 C++。和提升
    • 哈哈。最后一个问题:当使用捆绑的顶点/边时,我在结构中看到的所有示例甚至是单个(比如说)uint32_t。为什么我不能直接使用 uint32_t 有什么限制吗?
    • 没有限制。只是好习惯。为什么要显着降低您的代码的通用性和非传统性?
    猜你喜欢
    • 1970-01-01
    • 2018-04-08
    • 2011-01-15
    • 1970-01-01
    • 2021-04-15
    • 2015-07-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多