1//
2// NumberParser.cpp
3//
4// Library: Foundation
5// Package: Core
6// Module: NumberParser
7//
8// Copyright (c) 2004-2006, Applied Informatics Software Engineering GmbH.
9// and Contributors.
10//
11// SPDX-License-Identifier: BSL-1.0
12//
13
14
15#include "Poco/NumberParser.h"
16#include "Poco/Exception.h"
17#include "Poco/String.h"
18#include "Poco/NumericString.h"
19#include <cstdio>
20#include <cctype>
21#include <stdlib.h>
22#if !defined(POCO_NO_LOCALE)
23 #include <locale>
24#endif
25
26
27#if defined(POCO_LONG_IS_64_BIT)
28 #define I64_FMT "l"
29#elif defined(_MSC_VER) || defined(__MINGW32__)
30 #define I64_FMT "I64"
31#elif defined(__APPLE__)
32 #define I64_FMT "q"
33#else
34 #define I64_FMT "ll"
35#endif
36
37
38namespace Poco {
39
40
41int NumberParser::parse(const std::string& s, char thSep)
42{
43 int result;
44 if (tryParse(s, result, thSep))
45 return result;
46 else
47 throw SyntaxException("Not a valid integer", s);
48}
49
50
51bool NumberParser::tryParse(const std::string& s, int& value, char thSep)
52{
53 return strToInt(s.c_str(), value, NUM_BASE_DEC, thSep);
54}
55
56
57unsigned NumberParser::parseUnsigned(const std::string& s, char thSep)
58{
59 unsigned result;
60 if (tryParseUnsigned(s, result, thSep))
61 return result;
62 else
63 throw SyntaxException("Not a valid unsigned integer", s);
64}
65
66
67bool NumberParser::tryParseUnsigned(const std::string& s, unsigned& value, char thSep)
68{
69 return strToInt(s.c_str(), value, NUM_BASE_DEC, thSep);
70}
71
72
73unsigned NumberParser::parseHex(const std::string& s)
74{
75 unsigned result;
76 if (tryParseHex(s, result))
77 return result;
78 else
79 throw SyntaxException("Not a valid hexadecimal integer", s);
80}
81
82
83bool NumberParser::tryParseHex(const std::string& s, unsigned& value)
84{
85 int offset = 0;
86 if (s.size() > 2 && s[0] == '0' && (s[1] == 'x' || s[1] == 'X')) offset = 2;
87 return strToInt(s.c_str() + offset, value, NUM_BASE_HEX);
88}
89
90
91unsigned NumberParser::parseOct(const std::string& s)
92{
93 unsigned result;
94 if (tryParseOct(s, result))
95 return result;
96 else
97 throw SyntaxException("Not a valid hexadecimal integer", s);
98}
99
100
101bool NumberParser::tryParseOct(const std::string& s, unsigned& value)
102{
103 return strToInt(s.c_str(), value, NUM_BASE_OCT);
104}
105
106
107#if defined(POCO_HAVE_INT64)
108
109
110Int64 NumberParser::parse64(const std::string& s, char thSep)
111{
112 Int64 result;
113 if (tryParse64(s, result, thSep))
114 return result;
115 else
116 throw SyntaxException("Not a valid integer", s);
117}
118
119
120bool NumberParser::tryParse64(const std::string& s, Int64& value, char thSep)
121{
122 return strToInt(s.c_str(), value, NUM_BASE_DEC, thSep);
123}
124
125
126UInt64 NumberParser::parseUnsigned64(const std::string& s, char thSep)
127{
128 UInt64 result;
129 if (tryParseUnsigned64(s, result, thSep))
130 return result;
131 else
132 throw SyntaxException("Not a valid unsigned integer", s);
133}
134
135
136bool NumberParser::tryParseUnsigned64(const std::string& s, UInt64& value, char thSep)
137{
138 return strToInt(s.c_str(), value, NUM_BASE_DEC, thSep);
139}
140
141
142UInt64 NumberParser::parseHex64(const std::string& s)
143{
144 UInt64 result;
145 if (tryParseHex64(s, result))
146 return result;
147 else
148 throw SyntaxException("Not a valid hexadecimal integer", s);
149}
150
151
152bool NumberParser::tryParseHex64(const std::string& s, UInt64& value)
153{
154 int offset = 0;
155 if (s.size() > 2 && s[0] == '0' && (s[1] == 'x' || s[1] == 'X')) offset = 2;
156 return strToInt(s.c_str() + offset, value, NUM_BASE_HEX);
157}
158
159
160UInt64 NumberParser::parseOct64(const std::string& s)
161{
162 UInt64 result;
163 if (tryParseOct64(s, result))
164 return result;
165 else
166 throw SyntaxException("Not a valid hexadecimal integer", s);
167}
168
169
170bool NumberParser::tryParseOct64(const std::string& s, UInt64& value)
171{
172 return strToInt(s.c_str(), value, NUM_BASE_OCT);
173}
174
175
176#endif // defined(POCO_HAVE_INT64)
177
178
179double NumberParser::parseFloat(const std::string& s, char decSep, char thSep)
180{
181 double result;
182 if (tryParseFloat(s, result, decSep, thSep))
183 return result;
184 else
185 throw SyntaxException("Not a valid floating-point number", s);
186}
187
188
189bool NumberParser::tryParseFloat(const std::string& s, double& value, char decSep, char thSep)
190{
191 return strToDouble(s.c_str(), value, decSep, thSep);
192}
193
194
195bool NumberParser::parseBool(const std::string& s)
196{
197 bool result;
198 if (tryParseBool(s, result))
199 return result;
200 else
201 throw SyntaxException("Not a valid bool number", s);
202}
203
204
205bool NumberParser::tryParseBool(const std::string& s, bool& value)
206{
207 int n;
208 if (NumberParser::tryParse(s, n))
209 {
210 value = (n != 0);
211 return true;
212 }
213
214 if (icompare(s, "true") == 0)
215 {
216 value = true;
217 return true;
218 }
219 else if (icompare(s, "yes") == 0)
220 {
221 value = true;
222 return true;
223 }
224 else if (icompare(s, "on") == 0)
225 {
226 value = true;
227 return true;
228 }
229
230 if (icompare(s, "false") == 0)
231 {
232 value = false;
233 return true;
234 }
235 else if (icompare(s, "no") == 0)
236 {
237 value = false;
238 return true;
239 }
240 else if (icompare(s, "off") == 0)
241 {
242 value = false;
243 return true;
244 }
245
246 return false;
247}
248
249
250} // namespace Poco
251