|
Boost Users : |
From: Dmitry (dmitry_at_[hidden])
Date: 2008-06-24 05:06:52
I have attached a draft version. I wrote it strictly following to the
instructions from boost::graph documentation
http://www.boost.org/doc/libs/1_35_0/libs/graph/doc/leda_conversion.html
What was really exciting is that after this I was able to call graph
algorithms (currently I have succided in calling Bellman Ford shortes
path, strongly connected components and minimal cycle ratio) without
data copying.
boost::bundle_property_map<> is quite suitable for creating boost
property maps from graphviz properties. In my current implementation its
usage is not completly generic. I think with enough motivation it would
take one day to make it 100% generic.
Waiting somebody motivates me,
Regards,
Dmitry
Max escribi¨®:
> Please give more details ...
> :-)
>
> Cheers
> Max
>
>> Hi there,
>>
>> I have a very nice BGL adaptor for AT&T graphviz
>> graph representation.
>> Is it worthy to add it to the boost library ?
>>
>> Thanks in advance,
>>
>> Sr. Dmitry
>
>
>
> ------------------------------------------------------------------------
>
> _______________________________________________
> Boost-users mailing list
> Boost-users_at_[hidden]
> http://lists.boost.org/mailman/listinfo.cgi/boost-users
#ifndef GRAPHVIZ_BGL_ADAPTOR_HPP
#define GRAPHVIZ_BGL_ADAPTOR_HPP
#include <stdexcept>
//#include <iostream>
#include <boost/config.hpp>
#include <boost/iterator/iterator_facade.hpp>
#include <boost/graph/graph_traits.hpp>
#include <boost/graph/properties.hpp>
#include <agraph.h>
namespace boost {
typedef Agraph_t* bgl_graphviz_t;
struct graphviz_traversal_category :
public virtual edge_list_graph_tag,
public virtual bidirectional_graph_tag,
public virtual adjacency_graph_tag,
public virtual vertex_list_graph_tag { };
template <> struct graph_traits<bgl_graphviz_t>
{
typedef Agnode_t* vertex_descriptor;
typedef Agedge_t* edge_descriptor;
struct vertex_iterator : public iterator_facade<vertex_iterator,
vertex_descriptor,
forward_traversal_tag,
const vertex_descriptor&>
{
explicit vertex_iterator(vertex_descriptor v = 0) : m_v(v) { }
const vertex_descriptor& dereference() const { return m_v; }
bool equal(const vertex_iterator& other) const
{
if (m_v == other.m_v) return true;
if (other.m_v == 0 || m_v == 0) return false;
return AGID(m_v) == AGID(other.m_v);
}
void increment()
{
m_v = agnxtnode(m_v);
}
private:
vertex_descriptor m_v;
};
struct edge_iterator : public iterator_facade<edge_iterator,
edge_descriptor,
forward_traversal_tag,
const edge_descriptor&>
{
explicit edge_iterator(vertex_descriptor v = 0, edge_descriptor e = 0) : m_v(v), m_base(e)
{ }
virtual ~edge_iterator() {}
protected:
virtual void increment()
{
if (m_base == 0) throw std::runtime_error("Out of range\n");
m_base = agnxtout(m_base);
if (m_base == 0)
{
m_v = agnxtnode(m_v);
if (m_v) m_base = agfstout(m_v);
}
}
const edge_descriptor& dereference() const { return m_base; }
bool equal(const edge_iterator& other) const
{
if (m_base == other.m_base) return true;
if (other.m_base == 0 || m_base == 0) return false;
return AGID(m_base) == AGID(other.m_base);
}
vertex_descriptor m_v;
edge_descriptor m_base;
friend class iterator_core_access;
};
struct out_edge_iterator : public iterator_facade<out_edge_iterator,
edge_descriptor,
forward_traversal_tag,
const edge_descriptor&>
{
explicit out_edge_iterator(vertex_descriptor v = 0, edge_descriptor e = 0) : m_v(v), m_base(e)
{}
protected:
const edge_descriptor& dereference() const { return m_base; }
void increment()
{
if (m_base == 0) throw std::runtime_error("Out of range\n");
m_base = agnxtout(m_base);
}
bool equal(const out_edge_iterator& other) const
{
if (m_base == other.m_base) return true;
if (other.m_base == 0 || m_base == 0) return false;
return AGID(m_base) == AGID(other.m_base);
}
vertex_descriptor m_v;
edge_descriptor m_base;
friend class iterator_core_access;
};
struct in_edge_iterator : public edge_iterator
{
explicit in_edge_iterator(vertex_descriptor v = 0, edge_descriptor e = 0) : edge_iterator(v, e)
{ }
void increment()
{
if (m_base == 0) throw std::runtime_error("Out of range\n");
m_base = agnxtin(m_base);
}
};
typedef boost::directed_tag directed_category;
typedef allow_parallel_edge_tag edge_parallel_category;
typedef graphviz_traversal_category traversal_category;
typedef unsigned vertices_size_type;
typedef int edges_size_type;
typedef int degree_size_type;
vertex_descriptor null_vertex() { return vertex_descriptor(0); }
};
inline std::pair<
graph_traits< bgl_graphviz_t >::edge_iterator,
graph_traits< bgl_graphviz_t >::edge_iterator >
edges(const bgl_graphviz_t& g)
{
typedef graph_traits< bgl_graphviz_t>::edge_iterator myIter;
bgl_graphviz_t &ncg = const_cast< bgl_graphviz_t&>(g);
return std::make_pair( myIter(agfstnode(ncg), agfstout(agfstnode(ncg))), myIter() );
}
inline std::pair<
graph_traits< bgl_graphviz_t >::vertex_iterator,
graph_traits< bgl_graphviz_t >::vertex_iterator >
vertices(const bgl_graphviz_t& g)
{
typedef graph_traits<bgl_graphviz_t >::vertex_iterator myIter;
Agraph_t* ncg = const_cast<bgl_graphviz_t>(g);
return std::make_pair( myIter(agfstnode(ncg)), myIter() );
}
inline graph_traits<bgl_graphviz_t>::vertex_descriptor
source(graph_traits<bgl_graphviz_t>::edge_descriptor e, const bgl_graphviz_t &g)
{
return agtail(e);
}
inline graph_traits<bgl_graphviz_t>::vertex_descriptor
target(graph_traits<bgl_graphviz_t>::edge_descriptor e, const bgl_graphviz_t &g)
{
return aghead(e);
}
inline std::pair<
graph_traits<bgl_graphviz_t>::out_edge_iterator,
graph_traits<bgl_graphviz_t >::out_edge_iterator >
out_edges( graph_traits< bgl_graphviz_t>::vertex_descriptor v, const bgl_graphviz_t &g)
{
typedef graph_traits< bgl_graphviz_t >::out_edge_iterator myIter;
return std::make_pair( myIter(v, agfstout(v)), myIter(v) );
}
inline graph_traits<Agraph_t*>::degree_size_type
out_degree(graph_traits<Agraph_t*>::vertex_descriptor v, const bgl_graphviz_t &g)
{
return agdegree(v, FALSE, TRUE);
}
inline graph_traits< bgl_graphviz_t >::vertices_size_type
num_vertices(const bgl_graphviz_t& g)
{
return agnnodes(const_cast<bgl_graphviz_t>(g));
}
inline graph_traits<bgl_graphviz_t>::edges_size_type
num_edges(const bgl_graphviz_t& g)
{
return agnedges(const_cast<bgl_graphviz_t>(g));
}
inline graph_traits<bgl_graphviz_t>::degree_size_type
in_degree(graph_traits<bgl_graphviz_t>::vertex_descriptor v, const bgl_graphviz_t& g)
{
return agdegree(v, TRUE, FALSE);
}
inline std::pair<
graph_traits<bgl_graphviz_t>::in_edge_iterator,
graph_traits<bgl_graphviz_t >::in_edge_iterator >
in_edges( graph_traits<bgl_graphviz_t>::vertex_descriptor v, const bgl_graphviz_t& g)
{
typedef graph_traits<bgl_graphviz_t>::in_edge_iterator myIter;
return std::make_pair( myIter(v, agfstin(v)), myIter(v) );
}
template <typename OBJ> struct graphviz_id_map
: public put_get_helper<int, graphviz_id_map<OBJ> >
{
typedef readable_property_map_tag category;
typedef int value_type;
typedef int reference;
typedef OBJ key_type; //Node or edge
graphviz_id_map() { }
int operator[](const OBJ& o) const { return AGID(o); }
};
/* inline graphviz_id_map
get(vertex_index_t, const bgl_graphviz_t& g)
{
return graphviz_id_map();
}*/
template <typename OBJ>
struct ltgraphviz {
bool operator()(const OBJ& o1, const OBJ& o2) const
{
return AGID(o1) < AGID(o2);
}
};
} // namespace boost
typedef boost::graphviz_id_map<Agnode_t*> vim1_t;
typedef boost::graphviz_id_map<Agedge_t*> eim1_t;
#endif //GRAPHVIZ_BGL_ADAPTOR_HPP
Boost-users list run by williamkempf at hotmail.com, kalb at libertysoft.com, bjorn.karlsson at readsoft.com, gregod at cs.rpi.edu, wekempf at cox.net