1#ifndef XRPL_TEST_CSF_DIGRAPH_H_INCLUDED
2#define XRPL_TEST_CSF_DIGRAPH_H_INCLUDED
4#include <boost/container/flat_map.hpp>
5#include <boost/range/adaptor/transformed.hpp>
6#include <boost/range/iterator_range.hpp>
35template <
class Vertex,
class EdgeData = detail::NoEdgeData>
38 using Links = boost::container::flat_map<Vertex, EdgeData>;
39 using Graph = boost::container::flat_map<Vertex, Links>;
55 connect(Vertex source, Vertex target, EdgeData e)
57 return graph_[source].emplace(target, e).second;
70 return connect(source, target, EdgeData{});
84 auto it =
graph_.find(source);
87 return it->second.erase(target) > 0;
100 edge(Vertex source, Vertex target)
const
102 auto it =
graph_.find(source);
105 auto edgeIt = it->second.find(target);
106 if (edgeIt != it->second.end())
107 return edgeIt->second;
132 return boost::adaptors::transform(
134 [](
typename Graph::value_type
const& v) {
return v.first; });
145 auto transform = [](
typename Links::value_type
const& link) {
148 auto it =
graph_.find(source);
150 return boost::adaptors::transform(it->second, transform);
152 return boost::adaptors::transform(
empty, transform);
173 auto transform = [source](
typename Links::value_type
const& link) {
174 return Edge{source, link.first, link.second};
177 auto it =
graph_.find(source);
179 return boost::adaptors::transform(it->second, transform);
181 return boost::adaptors::transform(
empty, transform);
192 auto it =
graph_.find(source);
194 return it->second.size();
206 template <
class VertexName>
210 out <<
"digraph {\n";
211 for (
auto const& [vertex, links] :
graph_)
213 auto const fromName = vertexName(vertex);
214 for (
auto const& eData : links)
216 auto const toName = vertexName(eData.first);
217 out << fromName <<
" -> " << toName <<
";\n";
223 template <
class VertexName>
bool connect(Vertex source, Vertex target)
Connect two vertices using default constructed edge data.
boost::container::flat_map< Vertex, EdgeData > Links
bool connected(Vertex source, Vertex target) const
Check if two vertices are connected.
boost::container::flat_map< Vertex, Links > Graph
auto outVertices() const
Range over vertices in the graph.
void saveDot(std::ostream &out, VertexName &&vertexName) const
Save GraphViz dot file.
auto outVertices(Vertex source) const
Range over target vertices.
auto outEdges(Vertex source) const
Range of out edges.
std::size_t outDegree(Vertex source) const
Vertex out-degree.
std::optional< EdgeData > edge(Vertex source, Vertex target) const
Return edge data between two vertices.
void saveDot(std::string const &fileName, VertexName &&vertexName) const
bool disconnect(Vertex source, Vertex target)
Disconnect two vertices.
bool connect(Vertex source, Vertex target, EdgeData e)
Connect two vertices.
Use hash_* containers for keys that do not need a cryptographically secure hashing algorithm.
Vertices and data associated with an Edge.