简体   繁体   English

用“纯”C ++ 11替代替换BGL迭代顶点?

[英]Replace BGL iterate over vertexes with “pure” C++11 alternative?

I want to replace the BGL iteration over vertexes or edges with pure C++11 equivalent. 我想用纯C ++ 11等效替换顶点或边上的BGL迭代。 The BGL code (from: http://www.boost.org/doc/libs/1_52_0/libs/graph/doc/quick_tour.html ) is: BGL代码(来自: http//www.boost.org/doc/libs/1_52_0/libs/graph/doc/quick_tour.html )是:

typename boost::graph_traits<Graph>::out_edge_iterator out_i, out_end;
typename boost::graph_traits<Graph>::edge_descriptor e;
for (std::tie(out_i, out_end) = out_edges(v, g);
     out_i != out_end; ++out_i)
{
  e = *out_i;
  Vertex src = source(e, g), targ = target(e, g);
  std::cout << "(" << name[get(vertex_id, src)]
            << "," << name[get(vertex_id, targ)] << ") ";
}

I tried several suggestions from here: Replace BOOST_FOREACH with "pure" C++11 alternative? 我从这里尝试了几个建议: 用“纯”C ++ 11替换替换BOOST_FOREACH? but without luck. 但没有运气。

I want to be able to write something like: 我希望能够写出如下内容:

for (auto &e : out_edges(v, g))
{ ... }

or something like: 或类似的东西:

for (std::tie(auto out_i, auto out_end) = out_edges(v, g);
     out_i != out_end; ++out_i)
{...}

Is it possible? 可能吗?

A simple wrapper over out_edges should suffice: out_edges一个简单包装应该足够了:

#include <boost/range/iterator_range.hpp>
#include <type_traits>

template<class T> using Invoke = typename T::type
template<class T> using RemoveRef = Invoke<std::remove_reference<T>>;
template<class G> using OutEdgeIterator = typename boost::graph_traits<G>::out_edge_iterator;

template<class V, class G>
auto out_edges_range(V&& v, G&& g)
  -> boost::iterator_range<OutEdgeIterator<RemoveRef<G>>>
{
  auto edge_pair = out_edges(std::forward<V>(v), std::forward<G>(g));
  return boost::make_iterator_range(edge_pair.first, edge_pair.second);
}

Or even simpler, a function that turns a std::pair into a valid range: 甚至更简单,一个将std::pair转换为有效范围的函数:

template<class It>
boost::iterator_range<It> pair_range(std::pair<It, It> const& p){
  return boost::make_iterator_range(p.first, p.second);
}

and then 然后

for(auto e : pair_range(out_edges(v, g))){
  // ...
}

Boost.Graph also provides convenience macros similar to BOOST_FOREACH but designed specifically for Graph iterations. Boost.Graph还提供类似于BOOST_FOREACH便捷宏,但专为Graph迭代而设计。

Iteration over all vertices/edges of a given graph is provided by macros BGL_FORALL_VERTICES / BGL_FORALL_EDGES and their template counterparts BGL_FORALL_VERTICES_T / BGL_FORALL_EDGES_T . 对给定图的所有顶点/边的迭代由宏BGL_FORALL_VERTICES / BGL_FORALL_EDGES及其模板对应物BGL_FORALL_VERTICES_T / BGL_FORALL_EDGES_T

Iteration over in- or out- edges of a given vertex is provided by macros BGL_FORALL_OUTEDGES or BGL_FORALL_INEDGES . 对给定顶点的内边缘或外边缘的迭代由宏BGL_FORALL_OUTEDGESBGL_FORALL_INEDGES (Add _T for their template versions). (为其模板版本添加_T)。 For adjacency vertices use BGL_FORALL_ADJ . 对于邻接顶点,使用BGL_FORALL_ADJ

Example: 例:

#include <boost/graph/iteration_macros.hpp>

typedef ... Graph;
Graph g;
BGL_FORALL_VERTICES(v, g, Graph)  //v is declared here and 
{                                   //is of type Graph::vertex_descriptor
     BGL_FORALL_OUTEDGES(v, e, g, Graph)  //e is declared as Graph::edge_descriptor
     {

     }
}

The macros work both in C++03 and C++11. 这些宏在C ++ 03和C ++ 11中都有效。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM