lexical_cast_old.hpp 5.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174
  1. // Copyright Kevlin Henney, 2000-2005.
  2. // Copyright Alexander Nasonov, 2006-2010.
  3. // Copyright Antony Polukhin, 2011-2023.
  4. //
  5. // Distributed under the Boost Software License, Version 1.0. (See
  6. // accompanying file LICENSE_1_0.txt or copy at
  7. // http://www.boost.org/LICENSE_1_0.txt)
  8. //
  9. // what: lexical_cast custom keyword cast
  10. // who: contributed by Kevlin Henney,
  11. // enhanced with contributions from Terje Slettebo,
  12. // with additional fixes and suggestions from Gennaro Prota,
  13. // Beman Dawes, Dave Abrahams, Daryle Walker, Peter Dimov,
  14. // Alexander Nasonov, Antony Polukhin, Justin Viiret, Michael Hofmann,
  15. // Cheng Yang, Matthew Bradbury, David W. Birdsall, Pavel Korzh and other Boosters
  16. // when: November 2000, March 2003, June 2005, June 2006, March 2011 - 2014
  17. #ifndef BOOST_LEXICAL_CAST_LEXICAL_CAST_OLD_HPP
  18. #define BOOST_LEXICAL_CAST_LEXICAL_CAST_OLD_HPP
  19. #include <boost/config.hpp>
  20. #ifdef BOOST_HAS_PRAGMA_ONCE
  21. # pragma once
  22. #endif
  23. #if defined(BOOST_NO_STRINGSTREAM) || defined(BOOST_NO_STD_WSTRING)
  24. #define BOOST_LCAST_NO_WCHAR_T
  25. #endif
  26. #include <climits>
  27. #include <cstddef>
  28. #include <string>
  29. #include <cstring>
  30. #include <cstdio>
  31. #include <boost/limits.hpp>
  32. #include <boost/type_traits/is_pointer.hpp>
  33. #include <boost/detail/lcast_precision.hpp>
  34. #include <boost/detail/workaround.hpp>
  35. #ifdef BOOST_NO_STRINGSTREAM
  36. #include <strstream>
  37. #else
  38. #include <sstream>
  39. #endif
  40. #include <boost/lexical_cast/bad_lexical_cast.hpp>
  41. #include <boost/lexical_cast/detail/widest_char.hpp>
  42. namespace boost {
  43. namespace detail
  44. {
  45. // selectors for choosing stream character type
  46. template<typename Type>
  47. struct stream_char
  48. {
  49. typedef char type;
  50. };
  51. #ifndef BOOST_LCAST_NO_WCHAR_T
  52. #ifndef BOOST_NO_INTRINSIC_WCHAR_T
  53. template<>
  54. struct stream_char<wchar_t>
  55. {
  56. typedef wchar_t type;
  57. };
  58. #endif
  59. template<>
  60. struct stream_char<wchar_t *>
  61. {
  62. typedef wchar_t type;
  63. };
  64. template<>
  65. struct stream_char<const wchar_t *>
  66. {
  67. typedef wchar_t type;
  68. };
  69. template<>
  70. struct stream_char<std::wstring>
  71. {
  72. typedef wchar_t type;
  73. };
  74. #endif
  75. // stream wrapper for handling lexical conversions
  76. template<typename Target, typename Source, typename Traits>
  77. class lexical_stream
  78. {
  79. private:
  80. typedef typename widest_char<
  81. typename stream_char<Target>::type,
  82. typename stream_char<Source>::type>::type char_type;
  83. typedef Traits traits_type;
  84. public:
  85. lexical_stream(char_type* = 0, char_type* = 0)
  86. {
  87. stream.unsetf(std::ios::skipws);
  88. lcast_set_precision(stream, static_cast<Source*>(0), static_cast<Target*>(0) );
  89. }
  90. ~lexical_stream()
  91. {
  92. #if defined(BOOST_NO_STRINGSTREAM)
  93. stream.freeze(false);
  94. #endif
  95. }
  96. bool operator<<(const Source &input)
  97. {
  98. return !(stream << input).fail();
  99. }
  100. template<typename InputStreamable>
  101. bool operator>>(InputStreamable &output)
  102. {
  103. return !is_pointer<InputStreamable>::value &&
  104. stream >> output &&
  105. stream.get() == traits_type::eof();
  106. }
  107. bool operator>>(std::string &output)
  108. {
  109. #if defined(BOOST_NO_STRINGSTREAM)
  110. stream << '\0';
  111. #endif
  112. stream.str().swap(output);
  113. return true;
  114. }
  115. #ifndef BOOST_LCAST_NO_WCHAR_T
  116. bool operator>>(std::wstring &output)
  117. {
  118. stream.str().swap(output);
  119. return true;
  120. }
  121. #endif
  122. private:
  123. #if defined(BOOST_NO_STRINGSTREAM)
  124. std::strstream stream;
  125. #elif defined(BOOST_NO_STD_LOCALE)
  126. std::stringstream stream;
  127. #else
  128. std::basic_stringstream<char_type,traits_type> stream;
  129. #endif
  130. };
  131. }
  132. // call-by-value fallback version (deprecated)
  133. template<typename Target, typename Source>
  134. Target lexical_cast(Source arg)
  135. {
  136. typedef typename detail::widest_char<
  137. typename detail::stream_char<Target>::type
  138. , typename detail::stream_char<Source>::type
  139. >::type char_type;
  140. typedef std::char_traits<char_type> traits;
  141. detail::lexical_stream<Target, Source, traits> interpreter;
  142. Target result;
  143. if(!(interpreter << arg && interpreter >> result))
  144. boost::conversion::detail::throw_bad_cast<Source, Target>();
  145. return result;
  146. }
  147. } // namespace boost
  148. #undef BOOST_LCAST_NO_WCHAR_T
  149. #endif // BOOST_LEXICAL_CAST_LEXICAL_CAST_OLD_HPP