File indexing completed on 2025-01-18 09:39:14
0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018 #ifndef BOOST_LEXICAL_CAST_TRY_LEXICAL_CONVERT_HPP
0019 #define BOOST_LEXICAL_CAST_TRY_LEXICAL_CONVERT_HPP
0020
0021 #include <boost/config.hpp>
0022 #ifdef BOOST_HAS_PRAGMA_ONCE
0023 # pragma once
0024 #endif
0025
0026 #if defined(__clang__) || (defined(__GNUC__) && \
0027 !(defined(__INTEL_COMPILER) || defined(__ICL) || defined(__ICC) || defined(__ECC)) && \
0028 (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 6)))
0029 #pragma GCC diagnostic push
0030 #pragma GCC diagnostic ignored "-Wuninitialized"
0031 #pragma GCC diagnostic ignored "-Wsign-conversion"
0032 #endif
0033
0034
0035 #include <string>
0036 #include <boost/type_traits/is_integral.hpp>
0037 #include <boost/type_traits/type_identity.hpp>
0038 #include <boost/type_traits/conditional.hpp>
0039 #include <boost/type_traits/is_same.hpp>
0040 #include <boost/type_traits/is_arithmetic.hpp>
0041
0042 #include <boost/lexical_cast/detail/buffer_view.hpp>
0043 #include <boost/lexical_cast/detail/is_character.hpp>
0044 #include <boost/lexical_cast/detail/converter_numeric.hpp>
0045 #include <boost/lexical_cast/detail/converter_lexical.hpp>
0046
0047 #include <boost/container/container_fwd.hpp>
0048
0049 namespace boost {
0050 namespace detail
0051 {
0052 template<typename T>
0053 struct is_stdstring
0054 : boost::false_type
0055 {};
0056
0057 template<typename CharT, typename Traits, typename Alloc>
0058 struct is_stdstring< std::basic_string<CharT, Traits, Alloc> >
0059 : boost::true_type
0060 {};
0061
0062
0063
0064 template<typename T>
0065 struct is_booststring
0066 : boost::false_type
0067 {};
0068
0069 template<typename CharT, typename Traits, typename Alloc>
0070 struct is_booststring< boost::container::basic_string<CharT, Traits, Alloc> >
0071 : boost::true_type
0072 {};
0073
0074 template<typename Target, typename Source>
0075 struct is_arithmetic_and_not_xchars
0076 {
0077 typedef boost::integral_constant<
0078 bool,
0079 !(boost::detail::is_character<Target>::value) &&
0080 !(boost::detail::is_character<Source>::value) &&
0081 boost::is_arithmetic<Source>::value &&
0082 boost::is_arithmetic<Target>::value
0083 > type;
0084
0085 BOOST_STATIC_CONSTANT(bool, value = (
0086 type::value
0087 ));
0088 };
0089
0090
0091
0092
0093
0094 template<typename Target, typename Source>
0095 struct is_xchar_to_xchar
0096 {
0097 typedef boost::integral_constant<
0098 bool,
0099 sizeof(Source) == sizeof(Target) &&
0100 sizeof(Source) == sizeof(char) &&
0101 boost::detail::is_character<Target>::value &&
0102 boost::detail::is_character<Source>::value
0103 > type;
0104
0105 BOOST_STATIC_CONSTANT(bool, value = (
0106 type::value
0107 ));
0108 };
0109
0110 template<typename Target, typename Source>
0111 struct is_char_array_to_stdstring
0112 : boost::false_type
0113 {};
0114
0115 template<typename CharT, typename Traits, typename Alloc>
0116 struct is_char_array_to_stdstring< std::basic_string<CharT, Traits, Alloc>, CharT* >
0117 : boost::true_type
0118 {};
0119
0120 template<typename CharT, typename Traits, typename Alloc>
0121 struct is_char_array_to_stdstring< std::basic_string<CharT, Traits, Alloc>, const CharT* >
0122 : boost::true_type
0123 {};
0124
0125
0126
0127 template<typename Target, typename Source>
0128 struct is_char_array_to_booststring
0129 : boost::false_type
0130 {};
0131
0132 template<typename CharT, typename Traits, typename Alloc>
0133 struct is_char_array_to_booststring< boost::container::basic_string<CharT, Traits, Alloc>, CharT* >
0134 : boost::true_type
0135 {};
0136
0137 template<typename CharT, typename Traits, typename Alloc>
0138 struct is_char_array_to_booststring< boost::container::basic_string<CharT, Traits, Alloc>, const CharT* >
0139 : boost::true_type
0140 {};
0141
0142 template <typename Target, typename Source>
0143 struct copy_converter_impl
0144 {
0145
0146
0147 #if !defined(BOOST_NO_CXX11_RVALUE_REFERENCES) && (!defined(BOOST_MSVC) || BOOST_MSVC >= 1800)
0148 template <class T>
0149 static inline bool try_convert(T&& arg, Target& result) {
0150 result = static_cast<T&&>(arg);
0151 return true;
0152 }
0153 #else
0154 static inline bool try_convert(const Source& arg, Target& result) {
0155 result = arg;
0156 return true;
0157 }
0158 #endif
0159 };
0160 }
0161
0162 namespace conversion { namespace detail {
0163
0164 template <typename Target, typename Source>
0165 inline bool try_lexical_convert(const Source& arg, Target& result)
0166 {
0167 typedef typename boost::detail::array_to_pointer_decay<Source>::type src;
0168
0169 typedef boost::integral_constant<
0170 bool,
0171 boost::detail::is_xchar_to_xchar<Target, src >::value ||
0172 boost::detail::is_char_array_to_stdstring<Target, src >::value ||
0173 boost::detail::is_char_array_to_booststring<Target, src >::value ||
0174 (
0175 boost::is_same<Target, src >::value &&
0176 (boost::detail::is_stdstring<Target >::value || boost::detail::is_booststring<Target >::value)
0177 ) ||
0178 (
0179 boost::is_same<Target, src >::value &&
0180 boost::detail::is_character<Target >::value
0181 )
0182 > shall_we_copy_t;
0183
0184 typedef boost::detail::is_arithmetic_and_not_xchars<Target, src >
0185 shall_we_copy_with_dynamic_check_t;
0186
0187
0188
0189 typedef typename boost::conditional<
0190 shall_we_copy_t::value,
0191 boost::type_identity<boost::detail::copy_converter_impl<Target, src > >,
0192 boost::conditional<
0193 shall_we_copy_with_dynamic_check_t::value,
0194 boost::detail::dynamic_num_converter_impl<Target, src >,
0195 boost::detail::lexical_converter_impl<Target, src >
0196 >
0197 >::type caster_type_lazy;
0198
0199 typedef typename caster_type_lazy::type caster_type;
0200
0201 return caster_type::try_convert(arg, result);
0202 }
0203
0204 template <typename Target, typename CharacterT>
0205 inline bool try_lexical_convert(const CharacterT* chars, std::size_t count, Target& result)
0206 {
0207 static_assert(
0208 boost::detail::is_character<CharacterT>::value,
0209 "This overload of try_lexical_convert is meant to be used only with arrays of characters."
0210 );
0211 return ::boost::conversion::detail::try_lexical_convert(
0212 ::boost::conversion::detail::make_buffer_view(chars, chars + count),
0213 result
0214 );
0215 }
0216
0217 }}
0218
0219 namespace conversion {
0220
0221 using ::boost::conversion::detail::try_lexical_convert;
0222 }
0223
0224 }
0225
0226 #if defined(__clang__) || (defined(__GNUC__) && \
0227 !(defined(__INTEL_COMPILER) || defined(__ICL) || defined(__ICC) || defined(__ECC)) && \
0228 (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 6)))
0229 #pragma GCC diagnostic pop
0230 #endif
0231
0232 #endif
0233