io.hpp 2.3 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485
  1. // Copyright (c) 2016-2021 Antony Polukhin
  2. //
  3. // Distributed under the Boost Software License, Version 1.0. (See accompanying
  4. // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
  5. #ifndef BOOST_PFR_DETAIL_IO_HPP
  6. #define BOOST_PFR_DETAIL_IO_HPP
  7. #pragma once
  8. #include <boost/pfr/detail/config.hpp>
  9. #include <boost/pfr/detail/sequence_tuple.hpp>
  10. #include <iosfwd> // stream operators
  11. #include <iomanip>
  12. #if defined(__has_include)
  13. # if __has_include(<string_view>) && BOOST_PFR_USE_CPP17
  14. # include <string_view>
  15. # endif
  16. #endif
  17. namespace boost { namespace pfr { namespace detail {
  18. inline auto quoted_helper(const std::string& s) noexcept {
  19. return std::quoted(s);
  20. }
  21. #if defined(__has_include)
  22. # if __has_include(<string_view>) && BOOST_PFR_USE_CPP17
  23. template <class CharT, class Traits>
  24. inline auto quoted_helper(std::basic_string_view<CharT, Traits> s) noexcept {
  25. return std::quoted(s);
  26. }
  27. # endif
  28. #endif
  29. inline auto quoted_helper(std::string& s) noexcept {
  30. return std::quoted(s);
  31. }
  32. template <class T>
  33. inline decltype(auto) quoted_helper(T&& v) noexcept {
  34. return std::forward<T>(v);
  35. }
  36. template <std::size_t I, std::size_t N>
  37. struct print_impl {
  38. template <class Stream, class T>
  39. static void print (Stream& out, const T& value) {
  40. if (!!I) out << ", ";
  41. out << detail::quoted_helper(boost::pfr::detail::sequence_tuple::get<I>(value));
  42. print_impl<I + 1, N>::print(out, value);
  43. }
  44. };
  45. template <std::size_t I>
  46. struct print_impl<I, I> {
  47. template <class Stream, class T> static void print (Stream&, const T&) noexcept {}
  48. };
  49. template <std::size_t I, std::size_t N>
  50. struct read_impl {
  51. template <class Stream, class T>
  52. static void read (Stream& in, const T& value) {
  53. char ignore = {};
  54. if (!!I) {
  55. in >> ignore;
  56. if (ignore != ',') in.setstate(Stream::failbit);
  57. in >> ignore;
  58. if (ignore != ' ') in.setstate(Stream::failbit);
  59. }
  60. in >> detail::quoted_helper( boost::pfr::detail::sequence_tuple::get<I>(value) );
  61. read_impl<I + 1, N>::read(in, value);
  62. }
  63. };
  64. template <std::size_t I>
  65. struct read_impl<I, I> {
  66. template <class Stream, class T> static void read (Stream&, const T&) {}
  67. };
  68. }}} // namespace boost::pfr::detail
  69. #endif // BOOST_PFR_DETAIL_IO_HPP