19#ifndef LIBSEMIGROUPS_DOT_HPP_ 
   20#define LIBSEMIGROUPS_DOT_HPP_ 
   30#include "exception.hpp"   
   31#include "libsemigroups/bipart.hpp" 
   34#include "detail/fmt.hpp"      
   35#include "detail/report.hpp"   
   39#ifndef LIBSEMIGROUPS_PARSED_BY_DOXYGEN 
   42    inline std::string 
const& dot_to_string(std::string 
const& x) {
 
   46    inline std::string& dot_to_string(std::string& x) {
 
   50    inline std::string&& dot_to_string(std::string&& x) {
 
   54    inline std::string dot_to_string(
char const* x) {
 
   55      return std::string(x);
 
   58    inline std::string dot_to_string(std::string_view x) {
 
   59      return std::string(x);
 
   62    template <
typename Thing>
 
   63    std::string dot_to_string(Thing&& thing) {
 
  141      template <
typename Thing>
 
  143          : 
attrs(), 
name(detail::dot_to_string(
std::forward<Thing>(thing))) {}
 
 
  183      template <
typename Thing1, 
typename Thing2>
 
  188        add_or_replace_attr(
attrs, key_str, val_str);
 
 
 
  212      template <
typename Thing1, 
typename Thing2>
 
  215            head(detail::dot_to_string(
std::forward<Thing1>(h))),
 
  216            tail(detail::dot_to_string(
std::forward<Thing2>(t))) {}
 
 
  239      template <
typename Thing1, 
typename Thing2>
 
  244        add_or_replace_attr(
attrs, key_str, val_str);
 
 
 
  290        = {
"#00ff00", 
"#ff00ff", 
"#007fff", 
"#ff7f00", 
"#7fbf7f", 
"#4604ac",
 
  291           "#de0328", 
"#19801d", 
"#d881f5", 
"#00ffff", 
"#ffff00", 
"#00ff7f",
 
  292           "#ad5867", 
"#85f610", 
"#84e9f5", 
"#f5c778", 
"#207090", 
"#764ef3",
 
  293           "#7b4c00", 
"#0000ff", 
"#b80c9a", 
"#601045", 
"#29b7c0", 
"#839f12"};
 
 
  373      return rx::iterator_range(_nodes.begin(), _nodes.end())
 
  374             | rx::transform([](
auto& pair) -> 
Node& { 
return pair.second; });
 
 
  387      return rx::iterator_range(_nodes.begin(), _nodes.end())
 
  389                 [](
auto& pair) -> 
Node const& { 
return pair.second; });
 
 
  506    template <
typename Thing1, 
typename Thing2>
 
  511      add_or_replace_attr(_attrs, key_str, val_str);
 
 
  534    template <
typename Thing>
 
  536      add_or_replace_attr(_attrs, key, 
"");
 
 
  549      return _nodes.count(
name);
 
 
  563    template <
typename Thing,
 
  564              typename std::enable_if_t<
 
  565                  !std::is_same_v<std::decay_t<Thing>, 
std::string>>>
 
  566    [[nodiscard]] 
bool is_node(Thing&& thing)
 const {
 
 
  585    template <
typename Thing>
 
  588      auto [it, inserted] = _nodes.emplace(name_str, 
Node(name_str));
 
 
  610    template <
typename Thing>
 
  613      auto it       = _nodes.find(name_str);
 
  614      if (it == _nodes.cend()) {
 
 
  637    template <
typename Thing1, 
typename Thing2>
 
  641      throw_if_not_node(head_str);
 
  642      throw_if_not_node(tail_str);
 
  643      _edges.emplace_back(head_str, tail_str);
 
  644      return _edges.back();
 
 
  667    template <
typename Thing1, 
typename Thing2>
 
  671      throw_if_not_node(head_str);
 
  672      throw_if_not_node(tail_str);
 
  674        return e.head == head_str && e.tail == tail_str;
 
  676      if (it == _edges.cend()) {
 
  678            "there is no edges from {} to {}!", head_str, tail_str);
 
 
  698    std::string_view edge_string() const noexcept;
 
  700    static 
void add_or_replace_attr(
std::map<
std::
string, 
std::
string>& 
attrs,
 
  701                                    std::
string const&                  key,
 
  702                                    std::
string const&                  val);
 
 
  753                                     std::
string const& sep = 
"::");
 
bool is_node(Thing &&thing) const
Check if there is a node with name obtained from an object.
Definition dot.hpp:566
auto nodes() noexcept
Returns a range object of references to the current nodes.
Definition dot.hpp:372
Dot & add_subgraph(Dot const &subgraph)
Add a Dot object as a subgraph.
auto nodes() const noexcept
Returns a range object of const references to the current nodes.
Definition dot.hpp:386
std::vector< Dot > const & subgraphs() const noexcept
Returns a const reference to the vector of subgraphs.
Definition dot.hpp:442
std::string to_human_readable_repr(Dot const &d)
Return a human readable representation of a Dot object.
Dot & add_attr(Thing &&key)
Add an attribute to the graph.
Definition dot.hpp:535
Node & node(Thing &&thing)
Return a node from the represented graph.
Definition dot.hpp:611
std::vector< Edge > & edges() noexcept
Returns a reference to the vector of edges.
Definition dot.hpp:401
Dot & add_subgraph(Dot &&subgraph)
Add a Dot object as a subgraph.
Dot & operator=(Dot &&)
Default move assignment operator.
static constexpr std::array< std::string_view, 24 > colors
An array of default HTML/hex colours.
Definition dot.hpp:290
Dot & add_attr(Thing1 &&key, Thing2 &&val)
Add an attribute to the graph.
Definition dot.hpp:507
Dot(Dot &&)
Default move constructor.
Dot(Dot const &)
Default copy constructor.
std::map< std::string, std::string > const & attrs() const noexcept
Returns a const reference to the map of attributes.
Definition dot.hpp:456
Node & add_node(Thing &&thing)
Add a node to the represented graph.
Definition dot.hpp:586
Dot()
Default constructor.
Dot & kind(Kind val) noexcept
Set the kind of the represented graph.
Definition dot.hpp:329
Edge & add_edge(Thing1 &&head, Thing2 &&tail)
Add an edge with given head and tail.
Definition dot.hpp:638
Dot & name(std::string const &val)
Set the name of the represented graph.
Definition dot.hpp:349
Dot & operator=(Dot const &)
Default copy assignment operator.
Kind
The kind of object represented.
Definition dot.hpp:276
@ subgraph
Definition dot.hpp:283
@ digraph
Value indicating that the represented graph has directed edges ->.
Definition dot.hpp:278
@ graph
Value indicating that the represented graph has undirected edges --.
Definition dot.hpp:280
std::string to_string() const
Convert a Dot object to a string.
bool is_node(std::string const &name) const
Check if there is a node with a given name.
Definition dot.hpp:548
std::vector< Dot > & subgraphs() noexcept
Returns a reference to the vector of subgraphs.
Definition dot.hpp:428
std::string const & name() const noexcept
Get the current name of the represented graph.
Definition dot.hpp:359
Edge & edge(Thing1 &&head, Thing2 &&tail)
Returns the first edge with given head and tail.
Definition dot.hpp:668
std::vector< Edge > const & edges() const noexcept
Returns a const reference to the vector of edges.
Definition dot.hpp:414
Kind kind() const noexcept
Get the kind of the represented graph.
Definition dot.hpp:340
#define LIBSEMIGROUPS_EXCEPTION(...)
Throw a LibsemigroupsException.
Definition exception.hpp:99
Namespace for everything in the libsemigroups library.
Definition action.hpp:44
This nested struct represents an edge in the represented graph.
Definition dot.hpp:198
std::string head
Name of the head of the edge.
Definition dot.hpp:269
Edge(Thing1 &&h, Thing2 &&t)
Construct from head and tail.
Definition dot.hpp:213
Edge & add_attr(Thing1 &&key, Thing2 &&val)
Add an attribute to an edge.
Definition dot.hpp:240
std::map< std::string, std::string > attrs
Map of attributes.
Definition dot.hpp:266
Edge & operator=(Edge &&)=default
Default move assignment.
std::string tail
Name of the tail of the edge.
Definition dot.hpp:272
std::string to_human_readable_repr(Dot::Edge const &e)
Return a human readable representation of a Dot::Edge object.
Edge & operator=(Edge const &)=default
Default copy assignment.
Edge()=default
Default constructor.
Edge(Edge &&)=default
Default move constructor.
Edge(Edge const &)=default
Default copy constructor.
This nested struct represents a node in the represented graph.
Definition dot.hpp:122
Node & operator=(Node &&)=default
Default move assignment.
Node(Node &&)=default
Default move constructor.
Node(Thing &&thing)
Construct from anything.
Definition dot.hpp:142
Node()=default
Default constructor.
std::map< std::string, std::string > attrs
Map containing the attributes of the Node.
Definition dot.hpp:124
std::string name
The name of the node.
Definition dot.hpp:127
Node(Node const &)=default
Default copy constructor.
Node & operator=(Node const &)=default
Default copy assignment.
std::string to_human_readable_repr(Dot::Node const &n)
Return a human readable representation of a Dot::Node object.
Node & add_attr(Thing1 &&key, Thing2 &&val)
Add an attribute to a node.
Definition dot.hpp:184