关于boost:BGL edge(u,v,g)具有用于边缘列表的自定义关联容器

BGL edge(u, v, g) with custom associative container for edge lists

我刚刚开始学习bgl,并在使用带有自定义顺序的std :: set作为adjacency_list中的边缘列表的容器时遇到了一个问题。我定义了operator <以根据边缘的属性对边缘进行排序,就像在ordered_out_edges.cpp示例中一样。这里boost :: edge_unique_ordering是一个自定义属性标签。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
template < typename Edge >
struct order_by_unique_order: public std::binary_function< Edge, Edge, bool >
{
    inline bool operator() (const Edge& e1, const Edge& e2) const
    {
        return boost::get(boost::edge_unique_ordering, e1) < boost::get(boost::edge_unique_ordering, e2);
    }
};

struct default_edge_containerS {};

namespace boost
{
    template < class ValueType >
    struct container_gen< default_edge_containerS, ValueType >
    {
        typedef std::set< ValueType, order_by_unique_order< ValueType > > type;
    };
}

通常它可以正常工作,但是当我使用edge(u,v,g)函数时,我遇到了迭代器异常。如果我将这些调用替换为一种变通方法,以避免通过(源,目标)请求边缘,则一切正常。

我仔细检查了升压代码,很确定原因是什么,我只是不确定这是否意味着我做错了,这是升压代码的问题,或只是没有记载的不兼容性。该函数在u的边缘列表容器上调用set :: find(StoredEdge(v))。现在默认的stored_edge :: operator <只是比较目标顶点,但是在我的情况下,我的自定义运算符<被调用,并且正在寻找的StoredEdge(v)显然是默认初始化的,没有任何属性,这大概是导致问题。在我看来,edge(u,v,g)应该严格基于目标顶点来搜索任何匹配项,而不管对容器内的边缘施加什么排序。

有人可以阐明我可能做错了什么或不理解吗?


您似乎需要编写一个package比较操作符,该操作符需要一个类型(将使用StoredEdge类型填充)并使用您的自定义比较功能在两个输入上比较get_target)的结果,使用类似的东西:

1
2
3
4
5
6
7
8
9
template <typename Cmp>
struct target_compare {
  Cmp cmp;
  target_compare(const Cmp& cmp): cmp(cmp) {}
  template <typename SE>
  bool operator()(const SE& a, const SE& b) const {
    return cmp(a.get_target(), b.get_target());
  }
};

然后在set中使用target_compare<order_by_unique_order<Edge> >作为比较类型。