-
Notifications
You must be signed in to change notification settings - Fork 22
/
Copy pathconstexpr_helper.hpp
163 lines (148 loc) · 4.07 KB
/
constexpr_helper.hpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
#pragma once
#include <string>
#include "constexpr_map.hpp"
#include "constexpr_unique_ptr.hpp"
#include "constexpr_variant.hpp"
namespace json
{
namespace soft_impl
{
constexpr int to_string_double_precision = 14;
template <typename elem_t>
constexpr bool is_digit(elem_t ch)
{
return '0' <= ch && ch <= '9';
}
template <typename string_t>
constexpr string_t to_string(unsigned long long value)
{
string_t result;
do {
result.push_back('0' + value % 10);
value /= 10;
} while (value > 0);
return string_t(result.rbegin(), result.rend());
}
template <typename string_t>
constexpr string_t to_string(long long value)
{
string_t result;
bool nega = false;
if (value == INT64_MIN) {
return to_string<string_t>(0x8000000000000000ull);
}
if (value < 0) {
nega = true;
value = -value;
}
do {
result.push_back('0' + value % 10);
value /= 10;
} while (value > 0);
if (nega) {
result.push_back('-');
}
return string_t(result.rbegin(), result.rend());
}
template <typename string_t>
constexpr string_t to_string(double value)
{
string_t result;
if (value < 0) {
result.push_back('-');
value = -value;
}
int precision = to_string_double_precision;
double base = 1;
int log_base = 0;
while (base <= value) {
base *= 10;
log_base++;
}
if (log_base == 0) {
while (base > value) {
base /= 10;
log_base--;
}
log_base++;
base *= 10;
result.push_back('0');
result.push_back('.');
for (int k = 0; k > log_base; k--) {
result.push_back('0');
}
}
while (precision--) {
log_base--;
base /= 10;
char c = '0';
while (value >= base) {
value -= base;
c++;
}
result.push_back(c);
if (log_base == 0) {
result.push_back('.');
}
}
if (log_base > 0) {
while (log_base > 0) {
result.push_back('0');
log_base--;
}
result.push_back('.');
}
return result;
}
template <typename string_t>
constexpr string_t to_string(signed char v)
{
return to_string<string_t>(static_cast<long long>(v));
}
template <typename string_t>
constexpr string_t to_string(short v)
{
return to_string<string_t>(static_cast<long long>(v));
}
template <typename string_t>
constexpr string_t to_string(int v)
{
return to_string<string_t>(static_cast<long long>(v));
}
template <typename string_t>
constexpr string_t to_string(long v)
{
return to_string<string_t>(static_cast<long long>(v));
}
template <typename string_t>
constexpr string_t to_string(unsigned char v)
{
return to_string<string_t>(static_cast<unsigned long long>(v));
}
template <typename string_t>
constexpr string_t to_string(unsigned short v)
{
return to_string<string_t>(static_cast<unsigned long long>(v));
}
template <typename string_t>
constexpr string_t to_string(unsigned int v)
{
return to_string<string_t>(static_cast<unsigned long long>(v));
}
template <typename string_t>
constexpr string_t to_string(unsigned long v)
{
return to_string<string_t>(static_cast<unsigned long long>(v));
}
template <typename string_t>
constexpr string_t to_string(float v)
{
return to_string<string_t>(static_cast<double>(v));
}
template <typename string_t>
constexpr string_t to_string(long double v)
{
return to_string<string_t>(static_cast<double>(v));
}
} // namespace soft_impl
}; // namespace json