Commit acfeb0ac authored by Tiago Peixoto's avatar Tiago Peixoto
Browse files

Implement hashing of edge descriptors

parent 32a06013
...@@ -12,6 +12,7 @@ ...@@ -12,6 +12,7 @@
#include <boost/tuple/tuple.hpp> #include <boost/tuple/tuple.hpp>
#include <boost/type_traits.hpp> #include <boost/type_traits.hpp>
#include <boost/mpl/if.hpp> #include <boost/mpl/if.hpp>
#include <functional>
#if BOOST_WORKAROUND(BOOST_MSVC, < 1300) #if BOOST_WORKAROUND(BOOST_MSVC, < 1300)
// Stay out of the way of the concept checking class // Stay out of the way of the concept checking class
...@@ -413,4 +414,23 @@ get_property(const reverse_graph<BidirectionalGraph,GRef>& g, Tag tag) ...@@ -413,4 +414,23 @@ get_property(const reverse_graph<BidirectionalGraph,GRef>& g, Tag tag)
} // namespace boost } // namespace boost
// hashing of edge descriptors
namespace std
{
template <class Edge>
struct hash<boost::detail::reverse_graph_edge_descriptor<Edge>>
{
template <class REdge>
std::size_t operator()(REdge const& e) const
{
return _h(Edge(e));
}
std::hash<Edge> _h;
};
} // namespace std
#endif #endif
...@@ -24,6 +24,7 @@ ...@@ -24,6 +24,7 @@
#include <numeric> #include <numeric>
#include <iostream> #include <iostream>
#include <tuple> #include <tuple>
#include <functional>
#include <boost/iterator.hpp> #include <boost/iterator.hpp>
#include <boost/graph/graph_traits.hpp> #include <boost/graph/graph_traits.hpp>
#include <boost/range/irange.hpp> #include <boost/range/irange.hpp>
...@@ -128,6 +129,36 @@ void remove_edge(const typename adj_list<Vertex>::edge_descriptor& e, ...@@ -128,6 +129,36 @@ void remove_edge(const typename adj_list<Vertex>::edge_descriptor& e,
// boost::adjacency_list with vector storage selectors for both vertex and edge // boost::adjacency_list with vector storage selectors for both vertex and edge
// lists. // lists.
namespace detail
{
template <class Vertex>
struct adj_edge_descriptor
{
adj_edge_descriptor()
: s(std::numeric_limits<Vertex>::max()),
t(std::numeric_limits<Vertex>::max()),
idx(std::numeric_limits<Vertex>::max()), inv(false) {};
adj_edge_descriptor(Vertex s, Vertex t, Vertex idx, bool inv)
: s(s), t(t), idx(idx), inv(inv) {}
bool operator==(const adj_edge_descriptor& other) const
{
return idx == other.idx;
}
bool operator!=(const adj_edge_descriptor& other) const
{
return idx != other.idx;
}
bool operator<(const adj_edge_descriptor& other) const
{
return idx < other.idx;
}
Vertex s, t, idx;
bool inv;
};
} // namespace detail
template <class Vertex = size_t> template <class Vertex = size_t>
class adj_list class adj_list
{ {
...@@ -135,31 +166,7 @@ public: ...@@ -135,31 +166,7 @@ public:
struct graph_tag {}; struct graph_tag {};
typedef Vertex vertex_t; typedef Vertex vertex_t;
struct edge_descriptor typedef detail::adj_edge_descriptor<Vertex> edge_descriptor;
{
edge_descriptor()
: s(std::numeric_limits<vertex_t>::max()),
t(std::numeric_limits<vertex_t>::max()),
idx(std::numeric_limits<vertex_t>::max()), inv(false) {};
edge_descriptor(vertex_t s, vertex_t t, vertex_t idx, bool inv)
: s(s), t(t), idx(idx), inv(inv) {}
bool operator==(const edge_descriptor& other) const
{
return idx == other.idx;
}
bool operator!=(const edge_descriptor& other) const
{
return idx != other.idx;
}
bool operator<(const edge_descriptor& other) const
{
return idx < other.idx;
}
vertex_t s, t, idx;
bool inv;
};
typedef std::vector<std::pair<vertex_t, vertex_t> > edge_list_t; typedef std::vector<std::pair<vertex_t, vertex_t> > edge_list_t;
typedef std::vector<edge_list_t> vertex_list_t; typedef std::vector<edge_list_t> vertex_list_t;
...@@ -994,4 +1001,23 @@ get(edge_index_t, const adj_list<Vertex>&) ...@@ -994,4 +1001,23 @@ get(edge_index_t, const adj_list<Vertex>&)
} // namespace boost } // namespace boost
// hashing of edge descriptors
namespace std
{
template <class Vertex>
struct hash<boost::detail::adj_edge_descriptor<Vertex>>
{
template <class Edge>
std::size_t operator()(Edge const& e) const
{
return _h(e.idx);
}
std::hash<Vertex> _h;
};
} // namespace std
#endif //GRAPH_ADJACENCY_HH #endif //GRAPH_ADJACENCY_HH
...@@ -22,11 +22,7 @@ ...@@ -22,11 +22,7 @@
#include <boost/version.hpp> #include <boost/version.hpp>
#include <boost/graph/graph_traits.hpp> #include <boost/graph/graph_traits.hpp>
#include <boost/graph/filtered_graph.hpp> #include <boost/graph/filtered_graph.hpp>
#if (BOOST_VERSION / 100 % 1000 >= 48) #include <boost/graph/reverse_graph_alt.hpp>
#include <boost/graph/reverse_graph_alt.hpp>
#else
#include <boost/graph/reverse_graph.hpp>
#endif
#include <boost/mpl/vector.hpp> #include <boost/mpl/vector.hpp>
#include <boost/mpl/erase.hpp> #include <boost/mpl/erase.hpp>
#include <boost/mpl/clear.hpp> #include <boost/mpl/clear.hpp>
......
...@@ -26,6 +26,9 @@ ...@@ -26,6 +26,9 @@
#include <utility> #include <utility>
#include <limits> #include <limits>
#include "graph_adjacency.hh"
#include <boost/graph/reverse_graph_alt.hpp>
#ifdef HAVE_SPARSEHASH #ifdef HAVE_SPARSEHASH
#include SPARSEHASH_INCLUDE(dense_hash_set) #include SPARSEHASH_INCLUDE(dense_hash_set)
#include SPARSEHASH_INCLUDE(dense_hash_map) #include SPARSEHASH_INCLUDE(dense_hash_map)
...@@ -92,6 +95,24 @@ struct empty_key<std::tuple<>> ...@@ -92,6 +95,24 @@ struct empty_key<std::tuple<>>
} }
}; };
template <class Vertex>
struct empty_key<boost::detail::adj_edge_descriptor<Vertex>>
{
static boost::detail::adj_edge_descriptor<Vertex> get()
{
return boost::detail::adj_edge_descriptor<Vertex>();
}
};
template <class Edge>
struct empty_key<boost::detail::reverse_graph_edge_descriptor<Edge>>
{
static boost::detail::reverse_graph_edge_descriptor<Edge> get()
{
auto e = empty_key<Edge>::get();
return boost::detail::reverse_graph_edge_descriptor<Edge>(e);
}
};
template <class Key> template <class Key>
struct deleted_key struct deleted_key
...@@ -157,6 +178,28 @@ struct deleted_key<std::tuple<>> ...@@ -157,6 +178,28 @@ struct deleted_key<std::tuple<>>
} }
}; };
template <class Vertex>
struct deleted_key<boost::detail::adj_edge_descriptor<Vertex>>
{
static boost::detail::adj_edge_descriptor<Vertex> get()
{
boost::detail::adj_edge_descriptor<Vertex> e;
e.idx--;
return e;
}
};
template <class Edge>
struct deleted_key<boost::detail::reverse_graph_edge_descriptor<Edge>>
{
static boost::detail::reverse_graph_edge_descriptor<Edge> get()
{
auto e = deleted_key<Edge>::get();
return boost::detail::reverse_graph_edge_descriptor<Edge>(e);
}
};
template<class Key, template<class Key,
class Hash = std::hash<Key>, class Hash = std::hash<Key>,
class Pred = std::equal_to<Key>, class Pred = std::equal_to<Key>,
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment