Utopia  2
Framework for studying models of complex & adaptive systems.
ostream.hh
Go to the documentation of this file.
1 #ifndef UTOPIA_CORE_OSTREAM_HH
2 #define UTOPIA_CORE_OSTREAM_HH
3 
4 #include "type_traits.hh"
5 
6 namespace Utopia::Utils {
7 
16 template < typename T, typename U >
17 std::ostream&
18 operator<<(std::ostream& out, const std::pair< T, U >& pair)
19 {
20  out << "(" << pair.first << ", " << pair.second << ")";
21  return out;
22 }
23 
32 template < class T >
33 std::enable_if_t< is_container_v< T >, std::ostream& >
34 operator<<(std::ostream& out, const T& container)
35 {
36  if (container.size() == 0)
37  {
38  out << "[]";
39  }
40  else
41  {
42  out << std::setprecision(16) << "[";
43 
44  for (auto it = container.begin();
45  it != std::next(std::begin(container), container.size() - 1);
46  ++it)
47  {
48  out << *it << ", "; // becomes a recursive call in case of nested
49  // containers
50  }
51  out << *std::next(std::begin(container), container.size() - 1) << "]";
52  }
53  return out;
54 }
55 
66 std::ostream&
67 operator<<(std::ostream& out, const std::vector< bool >& container)
68 {
69  if (container.size() == 0)
70  {
71  out << "[]" << std::endl;
72  }
73  else
74  {
75  out << "[";
76  for (std::size_t i = 0; i < container.size() - 1; ++i)
77  {
78  out << container[i] << ", ";
79  }
80  out << container.back() << "]";
81  }
82  return out;
83 }
84 
98 template < template < typename, typename, typename... > class MapType,
99  typename Key,
100  typename Value,
101  typename... Args >
102 std::enable_if_t<
103  is_associative_container_v< MapType< Key, Value, Args... > > or
104  is_unordered_associative_container_v< MapType< Key, Value, Args... > >,
105  std::ostream& >
106 operator<<(std::ostream& out, const MapType< Key, Value, Args... >& map)
107 {
108  if (map.size() == 0)
109  {
110  out << "[]";
111  }
112  else
113  {
114  out << "[";
115  for (auto it = map.begin();
116  it != std::next(map.begin(), map.size() - 1);
117  ++it)
118  {
119  out << *it << ", ";
120  }
121  out << *std::next(map.begin(), map.size() - 1) << "]";
122  }
123  return out;
124 }
125 
133 template < typename... Types >
134 std::ostream&
135 operator<<(std::ostream& ostr, std::tuple< Types... > tuple)
136 {
137  std::string val_str("(");
138 
139  auto report_val = [&val_str](auto&& val) {
140  val_str += std::to_string(val) + ", ";
141  };
142  boost::hana::for_each(tuple, report_val);
143 
144  // remove final comma
145  val_str.erase(val_str.end() - 2);
146  val_str += ")";
147 
148  ostr << val_str;
149  return ostr;
150 }
151 
152 
162 template < typename T >
163 std::string
164 str(T&& t)
165 {
166  std::stringstream s;
167  s << t;
168  return s.str();
169 }
170 
171 
172 } // namespace Utopia::Utils
173 
174 #endif
auto begin(zip< Containers... > &zipper)
Begin function like std::begin.
Definition: zip.hh:537
Definition: metaprogramming.hh:43
std::ostream & operator<<(std::ostream &out, const std::pair< T, U > &pair)
pretty print a pair
Definition: ostream.hh:18
Definition: parallel.hh:235