implement read() and print() functions for easier I/O

This commit is contained in:
Johannes Kapfhammer 2019-10-10 14:05:52 +02:00
parent a994e7d10d
commit 11b6ae9729
7 changed files with 67 additions and 38 deletions

View File

@ -1,4 +1,4 @@
// -*- compile-command: "g++ -Iinclude -D_GLIBCXX_DEBUG -fsanitize=address,undefined -g3 -ggdb3 -std=c++17 example.cpp -o example && SOI_COLOR=1 SOI_EOFCHECK=1 ./example <<< ''" -*- // -*- compile-command: "g++ -Iinclude -D_GLIBCXX_DEBUG -fsanitize=address,undefined -g3 -ggdb3 -std=c++17 example.cpp -o example && SOI_COLOR=1 SOI_EOFCHECK=1 ./example <<< '4 5 blub 3 1 4'" -*-
#include <soi> #include <soi>
inline std::string methodName(const std::string& prettyFunction) { inline std::string methodName(const std::string& prettyFunction) {
@ -17,18 +17,27 @@ struct A{
dbg("imbar"); dbg("imbar");
} }
void foo(int a=3, int b=5, string c="hi") const { void foo(int a=3, int b=5, string c="hi") const {
dbg(methodName(__PRETTY_FUNCTION__));
dbg("bar"); dbg("bar");
} }
}; };
signed main() { signed main() {
dbg(methodName(__PRETTY_FUNCTION__));
A a; A a;
a(); a();
a.foo(); a.foo();
a.bar(3,4,"hi"); a.bar(3,4,"hi");
int i = read_int();
int j = read_int();
print(i, j);
print("read string",read<string>());
print('h','e','l','l','o');
print("false",'=',false);
print("true",'=',true);
print(read_vector<int>(3));
int l=3, r=5; int l=3, r=5;
dbg(tuple{l, r}); dbg(tuple{l, r});
dbg(); dbg();
@ -48,4 +57,16 @@ signed main() {
dbg(map<int, string>{{3,"three"},{1,"one"}}); dbg(map<int, string>{{3,"three"},{1,"one"}});
dbg(tuple{unordered_map<int, string>{{3,"three"},{1,"one"}}}); dbg(tuple{unordered_map<int, string>{{3,"three"},{1,"one"}}});
dbg(unordered_set<int>{3,1,4}); dbg(unordered_set<int>{3,1,4});
print("v-- empty line");
print();
print("^-- empty line");
print("tuple",make_tuple(3, 1, 4, 1));
print(vector<int>{3,1,4,1,5,9,2,6});
print(vector<pair<int, int>>{{3,1},{4,1}});
print(vector<pair<int, vector<string>>>{{3,{"hi"}},{4,{"hello", "world"}}});
print(set<int>{3,1,4});
print(map<int, string>{{3,"three"},{1,"one"}});
print(tuple{unordered_map<int, string>{{3,"three"},{1,"one"}}});
print(unordered_set<int>{3,1,4});
} }

View File

@ -1,6 +1,7 @@
#include <algorithm> #include <algorithm>
#include <array> #include <array>
#include <bitset> #include <bitset>
#include <cassert>
#include <cmath> #include <cmath>
#include <complex> #include <complex>
#include <cstddef> #include <cstddef>

View File

@ -23,6 +23,8 @@
namespace soi { namespace soi {
namespace prettyprint {
template <typename T, typename TChar, typename TCharTraits> template <typename T, typename TChar, typename TCharTraits>
std::basic_ostream<TChar, TCharTraits> & std::basic_ostream<TChar, TCharTraits> &
print(std::basic_ostream<TChar, TCharTraits> &stream, const T &x); print(std::basic_ostream<TChar, TCharTraits> &stream, const T &x);
@ -110,13 +112,13 @@ struct pretty_print_container_helper {
if (it != the_end) { if (it != the_end) {
for (;;) { for (;;) {
::soi::print(stream, *it); ::soi::prettyprint::print(stream, *it);
if (++it == the_end) if (++it == the_end)
break; break;
if (delimiters_type::values.delimiter != NULL) if (delimiters_type::values.delimiter != NULL)
::soi::print(stream, delimiters_type::values.delimiter); ::soi::prettyprint::print(stream, delimiters_type::values.delimiter);
} }
} }
} }
@ -126,12 +128,12 @@ struct pretty_print_container_helper {
inline void operator()(ostream_type &stream) const { inline void operator()(ostream_type &stream) const {
if (delimiters_type::values.prefix != NULL) if (delimiters_type::values.prefix != NULL)
::soi::print(stream, delimiters_type::values.prefix); ::soi::prettyprint::print(stream, delimiters_type::values.prefix);
pretty_printer<T>::pretty_print_body(container_, stream); pretty_printer<T>::pretty_print_body(container_, stream);
if (delimiters_type::values.postfix != NULL) if (delimiters_type::values.postfix != NULL)
::soi::print(stream, delimiters_type::values.postfix); ::soi::prettyprint::print(stream, delimiters_type::values.postfix);
} }
private: private:
@ -151,16 +153,16 @@ struct pretty_print_container_helper<
static void pretty_print_body(const std::pair<T1, T2> &c, static void pretty_print_body(const std::pair<T1, T2> &c,
ostream_type &stream) { ostream_type &stream) {
::soi::print(stream, c.first); ::soi::prettyprint::print(stream, c.first);
if (pretty_print_container_helper<T, TChar, TCharTraits, if (pretty_print_container_helper<T, TChar, TCharTraits,
TDelimiters>::delimiters_type::values TDelimiters>::delimiters_type::values
.delimiter != NULL) .delimiter != NULL)
::soi::print( ::soi::prettyprint::print(
stream, stream,
pretty_print_container_helper<T, TChar, TCharTraits, pretty_print_container_helper<T, TChar, TCharTraits,
TDelimiters>::delimiters_type::values TDelimiters>::delimiters_type::values
.delimiter); .delimiter);
::soi::print(stream, c.second); ::soi::prettyprint::print(stream, c.second);
} }
}; };
@ -189,7 +191,7 @@ struct pretty_print_container_helper<
tuple_pretty_print(const element_type &c, ostream_type &stream, tuple_pretty_print(const element_type &c, ostream_type &stream,
typename std::conditional<sizeof...(Args) != 0, Int<0>, typename std::conditional<sizeof...(Args) != 0, Int<0>,
std::nullptr_t>::type) { std::nullptr_t>::type) {
::soi::print(stream, std::get<0>(c)); ::soi::prettyprint::print(stream, std::get<0>(c));
tuple_pretty_print(c, stream, Int<1>()); tuple_pretty_print(c, stream, Int<1>());
} }
@ -199,13 +201,13 @@ struct pretty_print_container_helper<
if (pretty_print_container_helper<T, TChar, TCharTraits, if (pretty_print_container_helper<T, TChar, TCharTraits,
TDelimiters>::delimiters_type::values TDelimiters>::delimiters_type::values
.delimiter != NULL) .delimiter != NULL)
::soi::print( ::soi::prettyprint::print(
stream, stream,
pretty_print_container_helper<T, TChar, TCharTraits, pretty_print_container_helper<T, TChar, TCharTraits,
TDelimiters>::delimiters_type::values TDelimiters>::delimiters_type::values
.delimiter); .delimiter);
::soi::print(stream, std::get<N>(c)); ::soi::prettyprint::print(stream, std::get<N>(c));
tuple_pretty_print(c, stream, Int<N + 1>()); tuple_pretty_print(c, stream, Int<N + 1>());
} }
@ -375,7 +377,7 @@ const delimiters_values<wchar_t>
// Type-erasing helper class for easy use of custom delimiters. // Type-erasing helper class for easy use of custom delimiters.
// Requires TCharTraits = std::char_traits<TChar> and TChar = char or wchar_t, // Requires TCharTraits = std::char_traits<TChar> and TChar = char or wchar_t,
// and MyDelims needs to be defined for TChar. Usage: "cout << // and MyDelims needs to be defined for TChar. Usage: "cout <<
// pretty_pretty_print::custom_delims<MyDelims>(x)". // pretty_prettyprint::custom_delims<MyDelims>(x)".
struct custom_delims_base { struct custom_delims_base {
virtual ~custom_delims_base() {} virtual ~custom_delims_base() {}
@ -455,22 +457,20 @@ private:
const size_type n; const size_type n;
}; };
} // namespace soi
/* /*
// Global accessor functions for the convenience wrappers // Global accessor functions for the convenience wrappers
template<typename T> template<typename T>
inline pretty_pretty_print::array_wrapper_n<T> pretty_pretty_print_array(const T inline pretty_prettyprint::array_wrapper_n<T> pretty_pretty_print_array(const T
* const a, size_t n) * const a, size_t n)
{ {
return pretty_pretty_print::array_wrapper_n<T>(a, n); return pretty_prettyprint::array_wrapper_n<T>(a, n);
} }
template <typename T> pretty_pretty_print::bucket_pretty_print_wrapper<T> template <typename T> pretty_prettyprint::bucket_pretty_print_wrapper<T>
bucket_pretty_print(const T & m, typename T::size_type n) bucket_pretty_print(const T & m, typename T::size_type n)
{ {
return pretty_pretty_print::bucket_pretty_print_wrapper<T>(m, n); return pretty_prettyprint::bucket_pretty_print_wrapper<T>(m, n);
} }
@ -479,18 +479,18 @@ return pretty_pretty_print::bucket_pretty_print_wrapper<T>(m, n);
*/ */
namespace soi {
// Pretty_Prints a container to the stream using default delimiters
template <typename T, typename TChar, typename TCharTraits> template <typename T, typename TChar, typename TCharTraits>
inline typename std::enable_if<::soi::is_container<T>::value, inline typename std::enable_if<::soi::prettyprint::is_container<T>::value,
std::basic_ostream<TChar, TCharTraits> &>::type std::basic_ostream<TChar, TCharTraits> &>::type
pretty_print(std::basic_ostream<TChar, TCharTraits> &stream, pretty_print(std::basic_ostream<TChar, TCharTraits> &stream,
const T &container) { const T &container) {
return ::soi::print( return ::soi::prettyprint::print(
stream, stream,
::soi::pretty_print_container_helper<T, TChar, TCharTraits>(container)); ::soi::prettyprint::pretty_print_container_helper<T, TChar, TCharTraits>(container));
} }
}// namespace prettyprint
} // namespace soi } // namespace soi
#endif // SOI_PRETTY_PRETTY_PRINT #endif // SOI_PRETTY_PRETTY_PRINT

View File

@ -172,7 +172,7 @@ T &&dbg_print(T &&value, std::string const& type, char const *file, int line,
const T &ref = value; const T &ref = value;
std::stringstream std::stringstream
value_buffer; // avoid nesting of dbg macros within print functions value_buffer; // avoid nesting of dbg macros within print functions
soi::print(value_buffer, ref); soi::prettyprint::print(value_buffer, ref);
std::cerr << ANSI_DEBUG << "[" << file << ":" << line << " (" << function_name std::cerr << ANSI_DEBUG << "[" << file << ":" << line << " (" << function_name
<< ")] " << ANSI_RESET << ANSI_EXPRESSION << ")] " << ANSI_RESET << ANSI_EXPRESSION

View File

@ -81,7 +81,7 @@ realloc(void *ptr, std::size_t new_size);
[[deprecated("malloc/free is evil. Use a vector.")]] void * [[deprecated("malloc/free is evil. Use a vector.")]] void *
free(void *ptr, std::size_t new_size); free(void *ptr, std::size_t new_size);
[[deprecated("new is evil. Use a vector.")]] void * //[[deprecated("new is evil. Use a vector.")]] void *
operator new(std::size_t sz); //operator new(std::size_t sz);
[[deprecated("delete is evil. Use a vector.")]] void //[[deprecated("delete is evil. Use a vector.")]] void
operator delete(void *ptr) noexcept; //operator delete(void *ptr) noexcept;

View File

@ -13,6 +13,8 @@
namespace soi { namespace soi {
namespace prettyprint {
template <typename TChar, typename TCharTraits> template <typename TChar, typename TCharTraits>
std::basic_ostream<TChar, TCharTraits> & std::basic_ostream<TChar, TCharTraits> &
pretty_print(std::basic_ostream<TChar, TCharTraits> &stream, const bool &x) { pretty_print(std::basic_ostream<TChar, TCharTraits> &stream, const bool &x) {
@ -84,7 +86,7 @@ pretty_print(std::basic_ostream<TChar, TCharTraits> &stream, char c) {
} }
template <typename T, typename TChar, typename TCharTraits> template <typename T, typename TChar, typename TCharTraits>
inline typename std::enable_if<!::soi::is_container<T>::value, inline typename std::enable_if<!::soi::prettyprint::is_container<T>::value,
std::basic_ostream<TChar, TCharTraits> &>::type std::basic_ostream<TChar, TCharTraits> &>::type
pretty_print(std::basic_ostream<TChar, TCharTraits> &stream, const T &x) { pretty_print(std::basic_ostream<TChar, TCharTraits> &stream, const T &x) {
return stream << x; return stream << x;
@ -93,8 +95,11 @@ pretty_print(std::basic_ostream<TChar, TCharTraits> &stream, const T &x) {
template <typename T, typename TChar, typename TCharTraits> template <typename T, typename TChar, typename TCharTraits>
std::basic_ostream<TChar, TCharTraits> & std::basic_ostream<TChar, TCharTraits> &
print(std::basic_ostream<TChar, TCharTraits> &stream, const T &x) { print(std::basic_ostream<TChar, TCharTraits> &stream, const T &x) {
return pretty_print(stream, x); return ::soi::prettyprint::pretty_print(stream, x);
} }
} // namespace prettyprint
} // namespace soi } // namespace soi
#endif // SOI_PRETTY #endif // SOI_PRETTY

View File

@ -74,9 +74,11 @@ soi_initializer soi_initializer_{false};
} // end namespace soi } // end namespace soi
#include "bits/soi-deprecate.hpp" #include "bits/soi-io.hpp"
#include "bits/include-all.hpp" #include "bits/include-all.hpp"
#include "bits/soi-deprecate.hpp"
#define int int64_t #define int int64_t
using namespace std; using namespace std;