]> git.lyx.org Git - lyx.git/blob - boost/boost/lexical_cast.hpp
Martin's changes to the Note inset.
[lyx.git] / boost / boost / lexical_cast.hpp
1 #ifndef BOOST_LEXICAL_CAST_INCLUDED
2 #define BOOST_LEXICAL_CAST_INCLUDED
3
4 // Boost lexical_cast.hpp header  -------------------------------------------//
5 //
6 // See http://www.boost.org for most recent version including documentation.
7 // See end of this header for rights and permissions.
8 //
9 // what:  lexical_cast custom keyword cast
10 // who:   contributed by Kevlin Henney,
11 //        enhanced with contributions from Terje Slettebø,
12 //        with additional fixes and suggestions from Gennaro Prota,
13 //        Beman Dawes, Dave Abrahams, Daryle Walker, Peter Dimov,
14 //        and other Boosters
15 // when:  November 2000, March 2003
16
17 #include <string>
18 #include <typeinfo>
19 #include <boost/config.hpp>
20 #include <boost/limits.hpp>
21 #include <boost/type_traits/is_pointer.hpp>
22
23 #ifdef BOOST_NO_STRINGSTREAM
24 #include <strstream>
25 #else
26 #include <sstream>
27 #endif
28
29 #if defined(BOOST_NO_STRINGSTREAM) || \
30     defined(BOOST_NO_STD_WSTRING) || \
31     defined(BOOST_NO_STD_LOCALE) || \
32     defined(BOOST_NO_CWCHAR) || \
33     defined(BOOST_MSVC) && (BOOST_MSVC <= 1200)
34 #define DISABLE_WIDE_CHAR_SUPPORT
35 #endif
36
37 #ifdef BOOST_NO_INTRINSIC_WCHAR_T
38 #include <cwchar>
39 #endif
40
41 namespace boost
42 {
43     // exception used to indicate runtime lexical_cast failure
44     class bad_lexical_cast : public std::bad_cast
45     {
46     public:
47         virtual ~bad_lexical_cast() throw()
48         {
49         }
50     };
51
52     namespace detail // actual underlying concrete exception type
53     {
54         template<typename Target, typename Source>
55         class no_lexical_conversion : public bad_lexical_cast
56         {
57         public:
58             no_lexical_conversion()
59               : description(
60                   std::string() + "bad lexical cast: " +
61                   "source type value could not be interpreted as target, Target=" +
62                   typeid(Target).name() + ", Source=" + typeid(Source).name())
63             {
64             }
65             virtual ~no_lexical_conversion() throw()
66             {
67             }
68             virtual const char *what() const throw()
69             {
70                 return description.c_str();
71             }
72         private:
73             const std::string description; // static initialization fails on MSVC6
74         };
75     }
76
77     namespace detail // selectors for choosing stream character type
78     {
79         template<typename Type>
80         struct stream_char
81         {
82             typedef char type;
83         };
84
85         #ifndef DISABLE_WIDE_CHAR_SUPPORT
86         template<>
87         struct stream_char<wchar_t>
88         {
89             typedef wchar_t type;
90         };
91
92         template<>
93         struct stream_char<wchar_t *>
94         {
95             typedef wchar_t type;
96         };
97
98         template<>
99         struct stream_char<const wchar_t *>
100         {
101             typedef wchar_t type;
102         };
103
104         template<>
105         struct stream_char<std::wstring>
106         {
107             typedef wchar_t type;
108         };
109         #endif
110
111         template<typename TargetChar, typename SourceChar>
112         struct widest_char
113         {
114             typedef TargetChar type;
115         };
116
117         template<>
118         struct widest_char<char, wchar_t>
119         {
120             typedef wchar_t type;
121         };
122     }
123     
124     namespace detail // stream wrapper for handling lexical conversions
125     {
126         template<typename Target, typename Source>
127         class lexical_stream
128         {
129         public:
130             lexical_stream()
131             {
132                 stream.unsetf(std::ios::skipws);
133
134                 if(std::numeric_limits<Target>::is_specialized)
135                     stream.precision(std::numeric_limits<Target>::digits10 + 1);
136                 else if(std::numeric_limits<Source>::is_specialized)
137                     stream.precision(std::numeric_limits<Source>::digits10 + 1);
138             }
139             ~lexical_stream()
140             {
141                 #if defined(BOOST_NO_STRINGSTREAM)
142                 stream.freeze(false);
143                 #endif
144             }
145             bool operator<<(const Source &input)
146             {
147                 return stream << input;
148             }
149             template<typename InputStreamable>
150             bool operator>>(InputStreamable &output)
151             {
152                 return !is_pointer<InputStreamable>::value &&
153                        stream >> output &&
154                        (stream >> std::ws).eof();
155             }
156             bool operator>>(std::string &output)
157             {
158                 #if defined(BOOST_NO_STRINGSTREAM)
159                 stream << '\0';
160                 #endif
161                 output = stream.str();
162                 return true;
163             }
164             #ifndef DISABLE_WIDE_CHAR_SUPPORT
165             bool operator>>(std::wstring &output)
166             {
167                 output = stream.str();
168                 return true;
169             }
170             #endif
171         private:
172             typedef typename widest_char<
173                 typename stream_char<Target>::type,
174                 typename stream_char<Source>::type>::type char_type;
175
176             #if defined(BOOST_NO_STRINGSTREAM)
177             std::strstream stream;
178             #elif defined(BOOST_NO_STD_LOCALE)
179             std::stringstream stream;
180             #else
181             std::basic_stringstream<char_type> stream;
182             #endif
183         };
184     }
185
186     template<typename Target, typename Source>
187     Target lexical_cast(Source arg)
188     {
189         detail::lexical_stream<Target, Source> interpreter;
190         Target result;
191
192         if(!(interpreter << arg && interpreter >> result))
193             throw detail::no_lexical_conversion<Target, Source>();
194         return result;
195     }
196 }
197
198 // Copyright Kevlin Henney, 2000-2003. All rights reserved.
199 //
200 // Permission to use, copy, modify, and distribute this software for any
201 // purpose is hereby granted without fee, provided that this copyright and
202 // permissions notice appear in all copies and derivatives.
203 //
204 // This software is provided "as is" without express or implied warranty.
205
206 #undef DISABLE_WIDE_CHAR_SUPPORT
207 #endif