itoa.h Source File

itoa.h Source File#

Composable Kernel: itoa.h Source File
itoa.h
Go to the documentation of this file.
1// Tencent is pleased to support the open source community by making RapidJSON available.
2//
3// Copyright (C) 2015 THL A29 Limited, a Tencent company, and Milo Yip.
4//
5// Licensed under the MIT License (the "License"); you may not use this file except
6// in compliance with the License. You may obtain a copy of the License at
7//
8// http://opensource.org/licenses/MIT
9//
10// Unless required by applicable law or agreed to in writing, software distributed
11// under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
12// CONDITIONS OF ANY KIND, either express or implied. See the License for the
13// specific language governing permissions and limitations under the License.
14
15#ifndef RAPIDJSON_ITOA_
16#define RAPIDJSON_ITOA_
17
18#include "../rapidjson.h"
19
21namespace internal {
22
23inline const char* GetDigitsLut()
24{
25 static const char cDigitsLut[200] = {
26 '0', '0', '0', '1', '0', '2', '0', '3', '0', '4', '0', '5', '0', '6', '0', '7', '0',
27 '8', '0', '9', '1', '0', '1', '1', '1', '2', '1', '3', '1', '4', '1', '5', '1', '6',
28 '1', '7', '1', '8', '1', '9', '2', '0', '2', '1', '2', '2', '2', '3', '2', '4', '2',
29 '5', '2', '6', '2', '7', '2', '8', '2', '9', '3', '0', '3', '1', '3', '2', '3', '3',
30 '3', '4', '3', '5', '3', '6', '3', '7', '3', '8', '3', '9', '4', '0', '4', '1', '4',
31 '2', '4', '3', '4', '4', '4', '5', '4', '6', '4', '7', '4', '8', '4', '9', '5', '0',
32 '5', '1', '5', '2', '5', '3', '5', '4', '5', '5', '5', '6', '5', '7', '5', '8', '5',
33 '9', '6', '0', '6', '1', '6', '2', '6', '3', '6', '4', '6', '5', '6', '6', '6', '7',
34 '6', '8', '6', '9', '7', '0', '7', '1', '7', '2', '7', '3', '7', '4', '7', '5', '7',
35 '6', '7', '7', '7', '8', '7', '9', '8', '0', '8', '1', '8', '2', '8', '3', '8', '4',
36 '8', '5', '8', '6', '8', '7', '8', '8', '8', '9', '9', '0', '9', '1', '9', '2', '9',
37 '3', '9', '4', '9', '5', '9', '6', '9', '7', '9', '8', '9', '9'};
38 return cDigitsLut;
39}
40
41inline char* u32toa(uint32_t value, char* buffer)
42{
43 RAPIDJSON_ASSERT(buffer != 0);
44
45 const char* cDigitsLut = GetDigitsLut();
46
47 if(value < 10000)
48 {
49 const uint32_t d1 = (value / 100) << 1;
50 const uint32_t d2 = (value % 100) << 1;
51
52 if(value >= 1000)
53 *buffer++ = cDigitsLut[d1];
54 if(value >= 100)
55 *buffer++ = cDigitsLut[d1 + 1];
56 if(value >= 10)
57 *buffer++ = cDigitsLut[d2];
58 *buffer++ = cDigitsLut[d2 + 1];
59 }
60 else if(value < 100000000)
61 {
62 // value = bbbbcccc
63 const uint32_t b = value / 10000;
64 const uint32_t c = value % 10000;
65
66 const uint32_t d1 = (b / 100) << 1;
67 const uint32_t d2 = (b % 100) << 1;
68
69 const uint32_t d3 = (c / 100) << 1;
70 const uint32_t d4 = (c % 100) << 1;
71
72 if(value >= 10000000)
73 *buffer++ = cDigitsLut[d1];
74 if(value >= 1000000)
75 *buffer++ = cDigitsLut[d1 + 1];
76 if(value >= 100000)
77 *buffer++ = cDigitsLut[d2];
78 *buffer++ = cDigitsLut[d2 + 1];
79
80 *buffer++ = cDigitsLut[d3];
81 *buffer++ = cDigitsLut[d3 + 1];
82 *buffer++ = cDigitsLut[d4];
83 *buffer++ = cDigitsLut[d4 + 1];
84 }
85 else
86 {
87 // value = aabbbbcccc in decimal
88
89 const uint32_t a = value / 100000000; // 1 to 42
90 value %= 100000000;
91
92 if(a >= 10)
93 {
94 const unsigned i = a << 1;
95 *buffer++ = cDigitsLut[i];
96 *buffer++ = cDigitsLut[i + 1];
97 }
98 else
99 *buffer++ = static_cast<char>('0' + static_cast<char>(a));
100
101 const uint32_t b = value / 10000; // 0 to 9999
102 const uint32_t c = value % 10000; // 0 to 9999
103
104 const uint32_t d1 = (b / 100) << 1;
105 const uint32_t d2 = (b % 100) << 1;
106
107 const uint32_t d3 = (c / 100) << 1;
108 const uint32_t d4 = (c % 100) << 1;
109
110 *buffer++ = cDigitsLut[d1];
111 *buffer++ = cDigitsLut[d1 + 1];
112 *buffer++ = cDigitsLut[d2];
113 *buffer++ = cDigitsLut[d2 + 1];
114 *buffer++ = cDigitsLut[d3];
115 *buffer++ = cDigitsLut[d3 + 1];
116 *buffer++ = cDigitsLut[d4];
117 *buffer++ = cDigitsLut[d4 + 1];
118 }
119 return buffer;
120}
121
122inline char* i32toa(int32_t value, char* buffer)
123{
124 RAPIDJSON_ASSERT(buffer != 0);
125 uint32_t u = static_cast<uint32_t>(value);
126 if(value < 0)
127 {
128 *buffer++ = '-';
129 u = ~u + 1;
130 }
131
132 return u32toa(u, buffer);
133}
134
135inline char* u64toa(uint64_t value, char* buffer)
136{
137 RAPIDJSON_ASSERT(buffer != 0);
138 const char* cDigitsLut = GetDigitsLut();
139 const uint64_t kTen8 = 100000000;
140 const uint64_t kTen9 = kTen8 * 10;
141 const uint64_t kTen10 = kTen8 * 100;
142 const uint64_t kTen11 = kTen8 * 1000;
143 const uint64_t kTen12 = kTen8 * 10000;
144 const uint64_t kTen13 = kTen8 * 100000;
145 const uint64_t kTen14 = kTen8 * 1000000;
146 const uint64_t kTen15 = kTen8 * 10000000;
147 const uint64_t kTen16 = kTen8 * kTen8;
148
149 if(value < kTen8)
150 {
151 uint32_t v = static_cast<uint32_t>(value);
152 if(v < 10000)
153 {
154 const uint32_t d1 = (v / 100) << 1;
155 const uint32_t d2 = (v % 100) << 1;
156
157 if(v >= 1000)
158 *buffer++ = cDigitsLut[d1];
159 if(v >= 100)
160 *buffer++ = cDigitsLut[d1 + 1];
161 if(v >= 10)
162 *buffer++ = cDigitsLut[d2];
163 *buffer++ = cDigitsLut[d2 + 1];
164 }
165 else
166 {
167 // value = bbbbcccc
168 const uint32_t b = v / 10000;
169 const uint32_t c = v % 10000;
170
171 const uint32_t d1 = (b / 100) << 1;
172 const uint32_t d2 = (b % 100) << 1;
173
174 const uint32_t d3 = (c / 100) << 1;
175 const uint32_t d4 = (c % 100) << 1;
176
177 if(value >= 10000000)
178 *buffer++ = cDigitsLut[d1];
179 if(value >= 1000000)
180 *buffer++ = cDigitsLut[d1 + 1];
181 if(value >= 100000)
182 *buffer++ = cDigitsLut[d2];
183 *buffer++ = cDigitsLut[d2 + 1];
184
185 *buffer++ = cDigitsLut[d3];
186 *buffer++ = cDigitsLut[d3 + 1];
187 *buffer++ = cDigitsLut[d4];
188 *buffer++ = cDigitsLut[d4 + 1];
189 }
190 }
191 else if(value < kTen16)
192 {
193 const uint32_t v0 = static_cast<uint32_t>(value / kTen8);
194 const uint32_t v1 = static_cast<uint32_t>(value % kTen8);
195
196 const uint32_t b0 = v0 / 10000;
197 const uint32_t c0 = v0 % 10000;
198
199 const uint32_t d1 = (b0 / 100) << 1;
200 const uint32_t d2 = (b0 % 100) << 1;
201
202 const uint32_t d3 = (c0 / 100) << 1;
203 const uint32_t d4 = (c0 % 100) << 1;
204
205 const uint32_t b1 = v1 / 10000;
206 const uint32_t c1 = v1 % 10000;
207
208 const uint32_t d5 = (b1 / 100) << 1;
209 const uint32_t d6 = (b1 % 100) << 1;
210
211 const uint32_t d7 = (c1 / 100) << 1;
212 const uint32_t d8 = (c1 % 100) << 1;
213
214 if(value >= kTen15)
215 *buffer++ = cDigitsLut[d1];
216 if(value >= kTen14)
217 *buffer++ = cDigitsLut[d1 + 1];
218 if(value >= kTen13)
219 *buffer++ = cDigitsLut[d2];
220 if(value >= kTen12)
221 *buffer++ = cDigitsLut[d2 + 1];
222 if(value >= kTen11)
223 *buffer++ = cDigitsLut[d3];
224 if(value >= kTen10)
225 *buffer++ = cDigitsLut[d3 + 1];
226 if(value >= kTen9)
227 *buffer++ = cDigitsLut[d4];
228
229 *buffer++ = cDigitsLut[d4 + 1];
230 *buffer++ = cDigitsLut[d5];
231 *buffer++ = cDigitsLut[d5 + 1];
232 *buffer++ = cDigitsLut[d6];
233 *buffer++ = cDigitsLut[d6 + 1];
234 *buffer++ = cDigitsLut[d7];
235 *buffer++ = cDigitsLut[d7 + 1];
236 *buffer++ = cDigitsLut[d8];
237 *buffer++ = cDigitsLut[d8 + 1];
238 }
239 else
240 {
241 const uint32_t a = static_cast<uint32_t>(value / kTen16); // 1 to 1844
242 value %= kTen16;
243
244 if(a < 10)
245 *buffer++ = static_cast<char>('0' + static_cast<char>(a));
246 else if(a < 100)
247 {
248 const uint32_t i = a << 1;
249 *buffer++ = cDigitsLut[i];
250 *buffer++ = cDigitsLut[i + 1];
251 }
252 else if(a < 1000)
253 {
254 *buffer++ = static_cast<char>('0' + static_cast<char>(a / 100));
255
256 const uint32_t i = (a % 100) << 1;
257 *buffer++ = cDigitsLut[i];
258 *buffer++ = cDigitsLut[i + 1];
259 }
260 else
261 {
262 const uint32_t i = (a / 100) << 1;
263 const uint32_t j = (a % 100) << 1;
264 *buffer++ = cDigitsLut[i];
265 *buffer++ = cDigitsLut[i + 1];
266 *buffer++ = cDigitsLut[j];
267 *buffer++ = cDigitsLut[j + 1];
268 }
269
270 const uint32_t v0 = static_cast<uint32_t>(value / kTen8);
271 const uint32_t v1 = static_cast<uint32_t>(value % kTen8);
272
273 const uint32_t b0 = v0 / 10000;
274 const uint32_t c0 = v0 % 10000;
275
276 const uint32_t d1 = (b0 / 100) << 1;
277 const uint32_t d2 = (b0 % 100) << 1;
278
279 const uint32_t d3 = (c0 / 100) << 1;
280 const uint32_t d4 = (c0 % 100) << 1;
281
282 const uint32_t b1 = v1 / 10000;
283 const uint32_t c1 = v1 % 10000;
284
285 const uint32_t d5 = (b1 / 100) << 1;
286 const uint32_t d6 = (b1 % 100) << 1;
287
288 const uint32_t d7 = (c1 / 100) << 1;
289 const uint32_t d8 = (c1 % 100) << 1;
290
291 *buffer++ = cDigitsLut[d1];
292 *buffer++ = cDigitsLut[d1 + 1];
293 *buffer++ = cDigitsLut[d2];
294 *buffer++ = cDigitsLut[d2 + 1];
295 *buffer++ = cDigitsLut[d3];
296 *buffer++ = cDigitsLut[d3 + 1];
297 *buffer++ = cDigitsLut[d4];
298 *buffer++ = cDigitsLut[d4 + 1];
299 *buffer++ = cDigitsLut[d5];
300 *buffer++ = cDigitsLut[d5 + 1];
301 *buffer++ = cDigitsLut[d6];
302 *buffer++ = cDigitsLut[d6 + 1];
303 *buffer++ = cDigitsLut[d7];
304 *buffer++ = cDigitsLut[d7 + 1];
305 *buffer++ = cDigitsLut[d8];
306 *buffer++ = cDigitsLut[d8 + 1];
307 }
308
309 return buffer;
310}
311
312inline char* i64toa(int64_t value, char* buffer)
313{
314 RAPIDJSON_ASSERT(buffer != 0);
315 uint64_t u = static_cast<uint64_t>(value);
316 if(value < 0)
317 {
318 *buffer++ = '-';
319 u = ~u + 1;
320 }
321
322 return u64toa(u, buffer);
323}
324
325} // namespace internal
327
328#endif // RAPIDJSON_ITOA_
#define RAPIDJSON_ASSERT(x)
Assertion.
Definition rapidjson.h:451
#define RAPIDJSON_NAMESPACE_BEGIN
provide custom rapidjson namespace (opening expression)
Definition rapidjson.h:121
#define RAPIDJSON_NAMESPACE_END
provide custom rapidjson namespace (closing expression)
Definition rapidjson.h:124
Definition allocators.h:459
char * u64toa(uint64_t value, char *buffer)
Definition itoa.h:135
char * i64toa(int64_t value, char *buffer)
Definition itoa.h:312
const char * GetDigitsLut()
Definition itoa.h:23
char * u32toa(uint32_t value, char *buffer)
Definition itoa.h:41
char * i32toa(int32_t value, char *buffer)
Definition itoa.h:122
const GenericPointer< typename T::ValueType > T2 value
Definition pointer.h:1697
const GenericPointer< typename T::ValueType > T2 T::AllocatorType & a
Definition pointer.h:1517
common definitions and configuration
signed __int64 int64_t
Definition stdint.h:135
unsigned int uint32_t
Definition stdint.h:126
signed int int32_t
Definition stdint.h:123
unsigned __int64 uint64_t
Definition stdint.h:136