mirror of
https://github.com/fastfloat/fast_float.git
synced 2025-12-06 08:46:49 +08:00
harmonize files to use "east const"
manually checked modified files for errors, but not committing .clang-format due to the following warning: >>> Setting `QualifierAlignment` to something other than `Leave`, COULD lead to incorrect code formatting due to incorrect decisions made due to clang-formats lack of complete semantic information. As such extra care should be taken to review code changes made by the use of this option.
This commit is contained in:
parent
7f476cd259
commit
1a15c66fb9
38
README.md
38
README.md
@ -16,22 +16,22 @@ floating-point numbers with a C++17-like syntax (the library itself only
|
|||||||
requires C++11):
|
requires C++11):
|
||||||
|
|
||||||
```C++
|
```C++
|
||||||
from_chars_result from_chars(const char* first, const char* last, float& value, ...);
|
from_chars_result from_chars(char const *first, char const *last, float &value, ...);
|
||||||
from_chars_result from_chars(const char* first, const char* last, double& value, ...);
|
from_chars_result from_chars(char const *first, char const *last, double &value, ...);
|
||||||
```
|
```
|
||||||
|
|
||||||
You can also parse integer types:
|
You can also parse integer types:
|
||||||
|
|
||||||
```C++
|
```C++
|
||||||
from_chars_result from_chars(const char* first, const char* last, int& value, ...);
|
from_chars_result from_chars(char const *first, char const *last, int &value, ...);
|
||||||
from_chars_result from_chars(const char* first, const char* last, unsigned& value, ...);
|
from_chars_result from_chars(char const *first, char const *last, unsigned &value, ...);
|
||||||
```
|
```
|
||||||
|
|
||||||
The return type (`from_chars_result`) is defined as the struct:
|
The return type (`from_chars_result`) is defined as the struct:
|
||||||
|
|
||||||
```C++
|
```C++
|
||||||
struct from_chars_result {
|
struct from_chars_result {
|
||||||
const char* ptr;
|
char const *ptr;
|
||||||
std::errc ec;
|
std::errc ec;
|
||||||
};
|
};
|
||||||
```
|
```
|
||||||
@ -60,7 +60,7 @@ Example:
|
|||||||
#include <iostream>
|
#include <iostream>
|
||||||
|
|
||||||
int main() {
|
int main() {
|
||||||
const std::string input = "3.1416 xyz ";
|
std::string input = "3.1416 xyz ";
|
||||||
double result;
|
double result;
|
||||||
auto answer = fast_float::from_chars(input.data(), input.data() + input.size(), result);
|
auto answer = fast_float::from_chars(input.data(), input.data() + input.size(), result);
|
||||||
if (answer.ec != std::errc()) { std::cerr << "parsing failure\n"; return EXIT_FAILURE; }
|
if (answer.ec != std::errc()) { std::cerr << "parsing failure\n"; return EXIT_FAILURE; }
|
||||||
@ -72,7 +72,7 @@ int main() {
|
|||||||
You can parse delimited numbers:
|
You can parse delimited numbers:
|
||||||
|
|
||||||
```C++
|
```C++
|
||||||
const std::string input = "234532.3426362,7869234.9823,324562.645";
|
std::string input = "234532.3426362,7869234.9823,324562.645";
|
||||||
double result;
|
double result;
|
||||||
auto answer = fast_float::from_chars(input.data(), input.data() + input.size(), result);
|
auto answer = fast_float::from_chars(input.data(), input.data() + input.size(), result);
|
||||||
if (answer.ec != std::errc()) {
|
if (answer.ec != std::errc()) {
|
||||||
@ -143,26 +143,26 @@ following code will print the number 22250738585072012 three times:
|
|||||||
|
|
||||||
int main() {
|
int main() {
|
||||||
uint64_t i;
|
uint64_t i;
|
||||||
const char str[] = "22250738585072012";
|
std::string str = "22250738585072012";
|
||||||
auto answer = fast_float::from_chars(str, str + strlen(str), i);
|
auto answer = fast_float::from_chars(str.data(), str.data() + str.size(), i);
|
||||||
if (answer.ec != std::errc()) {
|
if (answer.ec != std::errc()) {
|
||||||
std::cerr << "parsing failure\n";
|
std::cerr << "parsing failure\n";
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
std::cout << "parsed the number "<< i << std::endl;
|
std::cout << "parsed the number "<< i << std::endl;
|
||||||
|
|
||||||
const char binstr[] = "1001111000011001110110111001001010110100111000110001100";
|
std::string binstr = "1001111000011001110110111001001010110100111000110001100";
|
||||||
|
|
||||||
answer = fast_float::from_chars(binstr, binstr + strlen(binstr), i, 2);
|
answer = fast_float::from_chars(binstr.data(), binstr.data() + binstr.size(), i, 2);
|
||||||
if (answer.ec != std::errc()) {
|
if (answer.ec != std::errc()) {
|
||||||
std::cerr << "parsing failure\n";
|
std::cerr << "parsing failure\n";
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
std::cout << "parsed the number "<< i << std::endl;
|
std::cout << "parsed the number "<< i << std::endl;
|
||||||
|
|
||||||
const char hexstr[] = "4f0cedc95a718c";
|
std::string hexstr = "4f0cedc95a718c";
|
||||||
|
|
||||||
answer = fast_float::from_chars(hexstr, hexstr + strlen(hexstr), i, 16);
|
answer = fast_float::from_chars(hexstr.data(), hexstr.data() + hexstr.size(), i, 16);
|
||||||
if (answer.ec != std::errc()) {
|
if (answer.ec != std::errc()) {
|
||||||
std::cerr << "parsing failure\n";
|
std::cerr << "parsing failure\n";
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
@ -259,7 +259,7 @@ following example:
|
|||||||
#include <iostream>
|
#include <iostream>
|
||||||
|
|
||||||
int main() {
|
int main() {
|
||||||
const std::u16string input = u"3.1416 xyz ";
|
std::u16string input = u"3.1416 xyz ";
|
||||||
double result;
|
double result;
|
||||||
auto answer = fast_float::from_chars(input.data(), input.data() + input.size(), result);
|
auto answer = fast_float::from_chars(input.data(), input.data() + input.size(), result);
|
||||||
if (answer.ec != std::errc()) { std::cerr << "parsing failure\n"; return EXIT_FAILURE; }
|
if (answer.ec != std::errc()) { std::cerr << "parsing failure\n"; return EXIT_FAILURE; }
|
||||||
@ -282,7 +282,7 @@ separator (e.g., the comma). You may use it as follows.
|
|||||||
#include <iostream>
|
#include <iostream>
|
||||||
|
|
||||||
int main() {
|
int main() {
|
||||||
const std::string input = "3,1416 xyz ";
|
std::string input = "3,1416 xyz ";
|
||||||
double result;
|
double result;
|
||||||
fast_float::parse_options options{fast_float::chars_format::general, ','};
|
fast_float::parse_options options{fast_float::chars_format::general, ','};
|
||||||
auto answer = fast_float::from_chars_advanced(input.data(), input.data() + input.size(), result, options);
|
auto answer = fast_float::from_chars_advanced(input.data(), input.data() + input.size(), result, options);
|
||||||
@ -299,7 +299,7 @@ int main() {
|
|||||||
#include <iostream>
|
#include <iostream>
|
||||||
|
|
||||||
int main() {
|
int main() {
|
||||||
const std::string input = "1d+4";
|
std::string input = "1d+4";
|
||||||
double result;
|
double result;
|
||||||
fast_float::parse_options options{fast_float::chars_format::fortran};
|
fast_float::parse_options options{fast_float::chars_format::fortran};
|
||||||
auto answer = fast_float::from_chars_advanced(input.data(), input.data() + input.size(), result, options);
|
auto answer = fast_float::from_chars_advanced(input.data(), input.data() + input.size(), result, options);
|
||||||
@ -316,7 +316,7 @@ int main() {
|
|||||||
#include <iostream>
|
#include <iostream>
|
||||||
|
|
||||||
int main() {
|
int main() {
|
||||||
const std::string input = "+.1"; // not valid
|
std::string input = "+.1"; // not valid
|
||||||
double result;
|
double result;
|
||||||
fast_float::parse_options options{fast_float::chars_format::json};
|
fast_float::parse_options options{fast_float::chars_format::json};
|
||||||
auto answer = fast_float::from_chars_advanced(input.data(), input.data() + input.size(), result, options);
|
auto answer = fast_float::from_chars_advanced(input.data(), input.data() + input.size(), result, options);
|
||||||
@ -332,7 +332,7 @@ By default the JSON format does not allow `inf`:
|
|||||||
#include <iostream>
|
#include <iostream>
|
||||||
|
|
||||||
int main() {
|
int main() {
|
||||||
const std::string input = "inf"; // not valid in JSON
|
std::string input = "inf"; // not valid in JSON
|
||||||
double result;
|
double result;
|
||||||
fast_float::parse_options options{fast_float::chars_format::json};
|
fast_float::parse_options options{fast_float::chars_format::json};
|
||||||
auto answer = fast_float::from_chars_advanced(input.data(), input.data() + input.size(), result, options);
|
auto answer = fast_float::from_chars_advanced(input.data(), input.data() + input.size(), result, options);
|
||||||
@ -348,7 +348,7 @@ You can allow it with a non-standard `json_or_infnan` variant:
|
|||||||
#include <iostream>
|
#include <iostream>
|
||||||
|
|
||||||
int main() {
|
int main() {
|
||||||
const std::string input = "inf"; // not valid in JSON but we allow it with json_or_infnan
|
std::string input = "inf"; // not valid in JSON but we allow it with json_or_infnan
|
||||||
double result;
|
double result;
|
||||||
fast_float::parse_options options{fast_float::chars_format::json_or_infnan};
|
fast_float::parse_options options{fast_float::chars_format::json_or_infnan};
|
||||||
auto answer = fast_float::from_chars_advanced(input.data(), input.data() + input.size(), result, options);
|
auto answer = fast_float::from_chars_advanced(input.data(), input.data() + input.size(), result, options);
|
||||||
|
|||||||
@ -19,7 +19,7 @@ fast_float::chars_format arbitrary_format(FuzzedDataProvider &fdp) {
|
|||||||
return chars_format::general;
|
return chars_format::general;
|
||||||
}
|
}
|
||||||
|
|
||||||
extern "C" int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) {
|
extern "C" int LLVMFuzzerTestOneInput(uint8_t const *data, size_t size) {
|
||||||
FuzzedDataProvider fdp(data, size);
|
FuzzedDataProvider fdp(data, size);
|
||||||
fast_float::chars_format format = arbitrary_format(fdp);
|
fast_float::chars_format format = arbitrary_format(fdp);
|
||||||
double result_d = 0.0;
|
double result_d = 0.0;
|
||||||
|
|||||||
@ -45,7 +45,7 @@ fastfloat_really_inline constexpr uint64_t byteswap(uint64_t val) {
|
|||||||
// Read 8 UC into a u64. Truncates UC if not char.
|
// Read 8 UC into a u64. Truncates UC if not char.
|
||||||
template <typename UC>
|
template <typename UC>
|
||||||
fastfloat_really_inline FASTFLOAT_CONSTEXPR20 uint64_t
|
fastfloat_really_inline FASTFLOAT_CONSTEXPR20 uint64_t
|
||||||
read8_to_u64(const UC *chars) {
|
read8_to_u64(UC const *chars) {
|
||||||
if (cpp20_and_in_constexpr() || !std::is_same<UC, char>::value) {
|
if (cpp20_and_in_constexpr() || !std::is_same<UC, char>::value) {
|
||||||
uint64_t val = 0;
|
uint64_t val = 0;
|
||||||
for (int i = 0; i < 8; ++i) {
|
for (int i = 0; i < 8; ++i) {
|
||||||
@ -65,9 +65,9 @@ read8_to_u64(const UC *chars) {
|
|||||||
|
|
||||||
#ifdef FASTFLOAT_SSE2
|
#ifdef FASTFLOAT_SSE2
|
||||||
|
|
||||||
fastfloat_really_inline uint64_t simd_read8_to_u64(const __m128i data) {
|
fastfloat_really_inline uint64_t simd_read8_to_u64(__m128i const data) {
|
||||||
FASTFLOAT_SIMD_DISABLE_WARNINGS
|
FASTFLOAT_SIMD_DISABLE_WARNINGS
|
||||||
const __m128i packed = _mm_packus_epi16(data, data);
|
__m128i const packed = _mm_packus_epi16(data, data);
|
||||||
#ifdef FASTFLOAT_64BIT
|
#ifdef FASTFLOAT_64BIT
|
||||||
return uint64_t(_mm_cvtsi128_si64(packed));
|
return uint64_t(_mm_cvtsi128_si64(packed));
|
||||||
#else
|
#else
|
||||||
@ -79,26 +79,26 @@ fastfloat_really_inline uint64_t simd_read8_to_u64(const __m128i data) {
|
|||||||
FASTFLOAT_SIMD_RESTORE_WARNINGS
|
FASTFLOAT_SIMD_RESTORE_WARNINGS
|
||||||
}
|
}
|
||||||
|
|
||||||
fastfloat_really_inline uint64_t simd_read8_to_u64(const char16_t *chars) {
|
fastfloat_really_inline uint64_t simd_read8_to_u64(char16_t const *chars) {
|
||||||
FASTFLOAT_SIMD_DISABLE_WARNINGS
|
FASTFLOAT_SIMD_DISABLE_WARNINGS
|
||||||
return simd_read8_to_u64(
|
return simd_read8_to_u64(
|
||||||
_mm_loadu_si128(reinterpret_cast<const __m128i *>(chars)));
|
_mm_loadu_si128(reinterpret_cast<__m128i const *>(chars)));
|
||||||
FASTFLOAT_SIMD_RESTORE_WARNINGS
|
FASTFLOAT_SIMD_RESTORE_WARNINGS
|
||||||
}
|
}
|
||||||
|
|
||||||
#elif defined(FASTFLOAT_NEON)
|
#elif defined(FASTFLOAT_NEON)
|
||||||
|
|
||||||
fastfloat_really_inline uint64_t simd_read8_to_u64(const uint16x8_t data) {
|
fastfloat_really_inline uint64_t simd_read8_to_u64(uint16x8_t const data) {
|
||||||
FASTFLOAT_SIMD_DISABLE_WARNINGS
|
FASTFLOAT_SIMD_DISABLE_WARNINGS
|
||||||
uint8x8_t utf8_packed = vmovn_u16(data);
|
uint8x8_t utf8_packed = vmovn_u16(data);
|
||||||
return vget_lane_u64(vreinterpret_u64_u8(utf8_packed), 0);
|
return vget_lane_u64(vreinterpret_u64_u8(utf8_packed), 0);
|
||||||
FASTFLOAT_SIMD_RESTORE_WARNINGS
|
FASTFLOAT_SIMD_RESTORE_WARNINGS
|
||||||
}
|
}
|
||||||
|
|
||||||
fastfloat_really_inline uint64_t simd_read8_to_u64(const char16_t *chars) {
|
fastfloat_really_inline uint64_t simd_read8_to_u64(char16_t const *chars) {
|
||||||
FASTFLOAT_SIMD_DISABLE_WARNINGS
|
FASTFLOAT_SIMD_DISABLE_WARNINGS
|
||||||
return simd_read8_to_u64(
|
return simd_read8_to_u64(
|
||||||
vld1q_u16(reinterpret_cast<const uint16_t *>(chars)));
|
vld1q_u16(reinterpret_cast<uint16_t const *>(chars)));
|
||||||
FASTFLOAT_SIMD_RESTORE_WARNINGS
|
FASTFLOAT_SIMD_RESTORE_WARNINGS
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -118,9 +118,9 @@ uint64_t simd_read8_to_u64(UC const *) {
|
|||||||
// credit @aqrit
|
// credit @aqrit
|
||||||
fastfloat_really_inline FASTFLOAT_CONSTEXPR14 uint32_t
|
fastfloat_really_inline FASTFLOAT_CONSTEXPR14 uint32_t
|
||||||
parse_eight_digits_unrolled(uint64_t val) {
|
parse_eight_digits_unrolled(uint64_t val) {
|
||||||
const uint64_t mask = 0x000000FF000000FF;
|
uint64_t const mask = 0x000000FF000000FF;
|
||||||
const uint64_t mul1 = 0x000F424000000064; // 100 + (1000000ULL << 32)
|
uint64_t const mul1 = 0x000F424000000064; // 100 + (1000000ULL << 32)
|
||||||
const uint64_t mul2 = 0x0000271000000001; // 1 + (10000ULL << 32)
|
uint64_t const mul2 = 0x0000271000000001; // 1 + (10000ULL << 32)
|
||||||
val -= 0x3030303030303030;
|
val -= 0x3030303030303030;
|
||||||
val = (val * 10) + (val >> 8); // val = (val * 2561) >> 8;
|
val = (val * 10) + (val >> 8); // val = (val * 2561) >> 8;
|
||||||
val = (((val & mask) * mul1) + (((val >> 16) & mask) * mul2)) >> 32;
|
val = (((val & mask) * mul1) + (((val >> 16) & mask) * mul2)) >> 32;
|
||||||
@ -150,20 +150,20 @@ is_made_of_eight_digits_fast(uint64_t val) noexcept {
|
|||||||
// Using this style (instead of is_made_of_eight_digits_fast() then
|
// Using this style (instead of is_made_of_eight_digits_fast() then
|
||||||
// parse_eight_digits_unrolled()) ensures we don't load SIMD registers twice.
|
// parse_eight_digits_unrolled()) ensures we don't load SIMD registers twice.
|
||||||
fastfloat_really_inline FASTFLOAT_CONSTEXPR20 bool
|
fastfloat_really_inline FASTFLOAT_CONSTEXPR20 bool
|
||||||
simd_parse_if_eight_digits_unrolled(const char16_t *chars,
|
simd_parse_if_eight_digits_unrolled(char16_t const *chars,
|
||||||
uint64_t &i) noexcept {
|
uint64_t &i) noexcept {
|
||||||
if (cpp20_and_in_constexpr()) {
|
if (cpp20_and_in_constexpr()) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
#ifdef FASTFLOAT_SSE2
|
#ifdef FASTFLOAT_SSE2
|
||||||
FASTFLOAT_SIMD_DISABLE_WARNINGS
|
FASTFLOAT_SIMD_DISABLE_WARNINGS
|
||||||
const __m128i data =
|
__m128i const data =
|
||||||
_mm_loadu_si128(reinterpret_cast<const __m128i *>(chars));
|
_mm_loadu_si128(reinterpret_cast<__m128i const *>(chars));
|
||||||
|
|
||||||
// (x - '0') <= 9
|
// (x - '0') <= 9
|
||||||
// http://0x80.pl/articles/simd-parsing-int-sequences.html
|
// http://0x80.pl/articles/simd-parsing-int-sequences.html
|
||||||
const __m128i t0 = _mm_add_epi16(data, _mm_set1_epi16(32720));
|
__m128i const t0 = _mm_add_epi16(data, _mm_set1_epi16(32720));
|
||||||
const __m128i t1 = _mm_cmpgt_epi16(t0, _mm_set1_epi16(-32759));
|
__m128i const t1 = _mm_cmpgt_epi16(t0, _mm_set1_epi16(-32759));
|
||||||
|
|
||||||
if (_mm_movemask_epi8(t1) == 0) {
|
if (_mm_movemask_epi8(t1) == 0) {
|
||||||
i = i * 100000000 + parse_eight_digits_unrolled(simd_read8_to_u64(data));
|
i = i * 100000000 + parse_eight_digits_unrolled(simd_read8_to_u64(data));
|
||||||
@ -173,12 +173,12 @@ simd_parse_if_eight_digits_unrolled(const char16_t *chars,
|
|||||||
FASTFLOAT_SIMD_RESTORE_WARNINGS
|
FASTFLOAT_SIMD_RESTORE_WARNINGS
|
||||||
#elif defined(FASTFLOAT_NEON)
|
#elif defined(FASTFLOAT_NEON)
|
||||||
FASTFLOAT_SIMD_DISABLE_WARNINGS
|
FASTFLOAT_SIMD_DISABLE_WARNINGS
|
||||||
const uint16x8_t data = vld1q_u16(reinterpret_cast<const uint16_t *>(chars));
|
uint16x8_t const data = vld1q_u16(reinterpret_cast<uint16_t const *>(chars));
|
||||||
|
|
||||||
// (x - '0') <= 9
|
// (x - '0') <= 9
|
||||||
// http://0x80.pl/articles/simd-parsing-int-sequences.html
|
// http://0x80.pl/articles/simd-parsing-int-sequences.html
|
||||||
const uint16x8_t t0 = vsubq_u16(data, vmovq_n_u16('0'));
|
uint16x8_t const t0 = vsubq_u16(data, vmovq_n_u16('0'));
|
||||||
const uint16x8_t mask = vcltq_u16(t0, vmovq_n_u16('9' - '0' + 1));
|
uint16x8_t const mask = vcltq_u16(t0, vmovq_n_u16('9' - '0' + 1));
|
||||||
|
|
||||||
if (vminvq_u16(mask) == 0xFFFF) {
|
if (vminvq_u16(mask) == 0xFFFF) {
|
||||||
i = i * 100000000 + parse_eight_digits_unrolled(simd_read8_to_u64(data));
|
i = i * 100000000 + parse_eight_digits_unrolled(simd_read8_to_u64(data));
|
||||||
@ -208,7 +208,7 @@ bool simd_parse_if_eight_digits_unrolled(UC const *, uint64_t &) {
|
|||||||
|
|
||||||
template <typename UC, FASTFLOAT_ENABLE_IF(!std::is_same<UC, char>::value) = 0>
|
template <typename UC, FASTFLOAT_ENABLE_IF(!std::is_same<UC, char>::value) = 0>
|
||||||
fastfloat_really_inline FASTFLOAT_CONSTEXPR20 void
|
fastfloat_really_inline FASTFLOAT_CONSTEXPR20 void
|
||||||
loop_parse_if_eight_digits(const UC *&p, const UC *const pend, uint64_t &i) {
|
loop_parse_if_eight_digits(UC const *&p, UC const *const pend, uint64_t &i) {
|
||||||
if (!has_simd_opt<UC>()) {
|
if (!has_simd_opt<UC>()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@ -220,7 +220,7 @@ loop_parse_if_eight_digits(const UC *&p, const UC *const pend, uint64_t &i) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
fastfloat_really_inline FASTFLOAT_CONSTEXPR20 void
|
fastfloat_really_inline FASTFLOAT_CONSTEXPR20 void
|
||||||
loop_parse_if_eight_digits(const char *&p, const char *const pend,
|
loop_parse_if_eight_digits(char const *&p, char const *const pend,
|
||||||
uint64_t &i) {
|
uint64_t &i) {
|
||||||
// optimizes better than parse_if_eight_digits_unrolled() for UC = char.
|
// optimizes better than parse_if_eight_digits_unrolled() for UC = char.
|
||||||
while ((std::distance(p, pend) >= 8) &&
|
while ((std::distance(p, pend) >= 8) &&
|
||||||
@ -259,12 +259,12 @@ template <typename UC> struct parsed_number_string_t {
|
|||||||
bool valid{false};
|
bool valid{false};
|
||||||
bool too_many_digits{false};
|
bool too_many_digits{false};
|
||||||
// contains the range of the significant digits
|
// contains the range of the significant digits
|
||||||
span<const UC> integer{}; // non-nullable
|
span<UC const> integer{}; // non-nullable
|
||||||
span<const UC> fraction{}; // nullable
|
span<UC const> fraction{}; // nullable
|
||||||
parse_error error{parse_error::no_error};
|
parse_error error{parse_error::no_error};
|
||||||
};
|
};
|
||||||
|
|
||||||
using byte_span = span<const char>;
|
using byte_span = span<char const>;
|
||||||
using parsed_number_string = parsed_number_string_t<char>;
|
using parsed_number_string = parsed_number_string_t<char>;
|
||||||
|
|
||||||
template <typename UC>
|
template <typename UC>
|
||||||
@ -328,7 +328,7 @@ parse_number_string(UC const *p, UC const *pend,
|
|||||||
}
|
}
|
||||||
UC const *const end_of_integer_part = p;
|
UC const *const end_of_integer_part = p;
|
||||||
int64_t digit_count = int64_t(end_of_integer_part - start_digits);
|
int64_t digit_count = int64_t(end_of_integer_part - start_digits);
|
||||||
answer.integer = span<const UC>(start_digits, size_t(digit_count));
|
answer.integer = span<UC const>(start_digits, size_t(digit_count));
|
||||||
if (uint64_t(fmt & detail::basic_json_fmt)) {
|
if (uint64_t(fmt & detail::basic_json_fmt)) {
|
||||||
// at least 1 digit in integer part, without leading zeros
|
// at least 1 digit in integer part, without leading zeros
|
||||||
if (digit_count == 0) {
|
if (digit_count == 0) {
|
||||||
@ -341,7 +341,7 @@ parse_number_string(UC const *p, UC const *pend,
|
|||||||
}
|
}
|
||||||
|
|
||||||
int64_t exponent = 0;
|
int64_t exponent = 0;
|
||||||
const bool has_decimal_point = (p != pend) && (*p == decimal_point);
|
bool const has_decimal_point = (p != pend) && (*p == decimal_point);
|
||||||
if (has_decimal_point) {
|
if (has_decimal_point) {
|
||||||
++p;
|
++p;
|
||||||
UC const *before = p;
|
UC const *before = p;
|
||||||
@ -355,7 +355,7 @@ parse_number_string(UC const *p, UC const *pend,
|
|||||||
i = i * 10 + digit; // in rare cases, this will overflow, but that's ok
|
i = i * 10 + digit; // in rare cases, this will overflow, but that's ok
|
||||||
}
|
}
|
||||||
exponent = before - p;
|
exponent = before - p;
|
||||||
answer.fraction = span<const UC>(before, size_t(p - before));
|
answer.fraction = span<UC const>(before, size_t(p - before));
|
||||||
digit_count -= exponent;
|
digit_count -= exponent;
|
||||||
}
|
}
|
||||||
if (uint64_t(fmt & detail::basic_json_fmt)) {
|
if (uint64_t(fmt & detail::basic_json_fmt)) {
|
||||||
@ -446,7 +446,7 @@ parse_number_string(UC const *p, UC const *pend,
|
|||||||
i = 0;
|
i = 0;
|
||||||
p = answer.integer.ptr;
|
p = answer.integer.ptr;
|
||||||
UC const *int_end = p + answer.integer.len();
|
UC const *int_end = p + answer.integer.len();
|
||||||
const uint64_t minimal_nineteen_digit_integer{1000000000000000000};
|
uint64_t const minimal_nineteen_digit_integer{1000000000000000000};
|
||||||
while ((i < minimal_nineteen_digit_integer) && (p != int_end)) {
|
while ((i < minimal_nineteen_digit_integer) && (p != int_end)) {
|
||||||
i = i * 10 + uint64_t(*p - UC('0'));
|
i = i * 10 + uint64_t(*p - UC('0'));
|
||||||
++p;
|
++p;
|
||||||
@ -498,7 +498,7 @@ parse_int_string(UC const *p, UC const *pend, T &value,
|
|||||||
++p;
|
++p;
|
||||||
}
|
}
|
||||||
|
|
||||||
const bool has_leading_zeros = p > start_num;
|
bool const has_leading_zeros = p > start_num;
|
||||||
|
|
||||||
UC const *const start_digits = p;
|
UC const *const start_digits = p;
|
||||||
|
|
||||||
|
|||||||
@ -43,8 +43,8 @@ template <uint16_t size> struct stackvec {
|
|||||||
uint16_t length{0};
|
uint16_t length{0};
|
||||||
|
|
||||||
stackvec() = default;
|
stackvec() = default;
|
||||||
stackvec(const stackvec &) = delete;
|
stackvec(stackvec const &) = delete;
|
||||||
stackvec &operator=(const stackvec &) = delete;
|
stackvec &operator=(stackvec const &) = delete;
|
||||||
stackvec(stackvec &&) = delete;
|
stackvec(stackvec &&) = delete;
|
||||||
stackvec &operator=(stackvec &&other) = delete;
|
stackvec &operator=(stackvec &&other) = delete;
|
||||||
|
|
||||||
@ -423,8 +423,8 @@ struct bigint : pow5_tables<> {
|
|||||||
stackvec<bigint_limbs> vec;
|
stackvec<bigint_limbs> vec;
|
||||||
|
|
||||||
FASTFLOAT_CONSTEXPR20 bigint() : vec() {}
|
FASTFLOAT_CONSTEXPR20 bigint() : vec() {}
|
||||||
bigint(const bigint &) = delete;
|
bigint(bigint const &) = delete;
|
||||||
bigint &operator=(const bigint &) = delete;
|
bigint &operator=(bigint const &) = delete;
|
||||||
bigint(bigint &&) = delete;
|
bigint(bigint &&) = delete;
|
||||||
bigint &operator=(bigint &&other) = delete;
|
bigint &operator=(bigint &&other) = delete;
|
||||||
|
|
||||||
@ -473,7 +473,7 @@ struct bigint : pow5_tables<> {
|
|||||||
// positive, this is larger, otherwise they are equal.
|
// positive, this is larger, otherwise they are equal.
|
||||||
// the limbs are stored in little-endian order, so we
|
// the limbs are stored in little-endian order, so we
|
||||||
// must compare the limbs in ever order.
|
// must compare the limbs in ever order.
|
||||||
FASTFLOAT_CONSTEXPR20 int compare(const bigint &other) const noexcept {
|
FASTFLOAT_CONSTEXPR20 int compare(bigint const &other) const noexcept {
|
||||||
if (vec.len() > other.vec.len()) {
|
if (vec.len() > other.vec.len()) {
|
||||||
return 1;
|
return 1;
|
||||||
} else if (vec.len() < other.vec.len()) {
|
} else if (vec.len() < other.vec.len()) {
|
||||||
@ -527,7 +527,7 @@ struct bigint : pow5_tables<> {
|
|||||||
} else if (!vec.is_empty()) {
|
} else if (!vec.is_empty()) {
|
||||||
// move limbs
|
// move limbs
|
||||||
limb *dst = vec.data + n;
|
limb *dst = vec.data + n;
|
||||||
const limb *src = vec.data;
|
limb const *src = vec.data;
|
||||||
std::copy_backward(src, src + vec.len(), dst + vec.len());
|
std::copy_backward(src, src + vec.len(), dst + vec.len());
|
||||||
// fill in empty limbs
|
// fill in empty limbs
|
||||||
limb *first = vec.data;
|
limb *first = vec.data;
|
||||||
|
|||||||
@ -20,7 +20,7 @@ namespace fast_float {
|
|||||||
template <int bit_precision>
|
template <int bit_precision>
|
||||||
fastfloat_really_inline FASTFLOAT_CONSTEXPR20 value128
|
fastfloat_really_inline FASTFLOAT_CONSTEXPR20 value128
|
||||||
compute_product_approximation(int64_t q, uint64_t w) {
|
compute_product_approximation(int64_t q, uint64_t w) {
|
||||||
const int index = 2 * int(q - powers::smallest_power_of_five);
|
int const index = 2 * int(q - powers::smallest_power_of_five);
|
||||||
// For small values of q, e.g., q in [0,27], the answer is always exact
|
// For small values of q, e.g., q in [0,27], the answer is always exact
|
||||||
// because The line value128 firstproduct = full_multiplication(w,
|
// because The line value128 firstproduct = full_multiplication(w,
|
||||||
// power_of_five_128[index]); gives the exact answer.
|
// power_of_five_128[index]); gives the exact answer.
|
||||||
|
|||||||
@ -143,8 +143,8 @@ template <typename callback>
|
|||||||
fastfloat_really_inline FASTFLOAT_CONSTEXPR14 void
|
fastfloat_really_inline FASTFLOAT_CONSTEXPR14 void
|
||||||
round_nearest_tie_even(adjusted_mantissa &am, int32_t shift,
|
round_nearest_tie_even(adjusted_mantissa &am, int32_t shift,
|
||||||
callback cb) noexcept {
|
callback cb) noexcept {
|
||||||
const uint64_t mask = (shift == 64) ? UINT64_MAX : (uint64_t(1) << shift) - 1;
|
uint64_t const mask = (shift == 64) ? UINT64_MAX : (uint64_t(1) << shift) - 1;
|
||||||
const uint64_t halfway = (shift == 0) ? 0 : uint64_t(1) << (shift - 1);
|
uint64_t const halfway = (shift == 0) ? 0 : uint64_t(1) << (shift - 1);
|
||||||
uint64_t truncated_bits = am.mantissa & mask;
|
uint64_t truncated_bits = am.mantissa & mask;
|
||||||
bool is_above = truncated_bits > halfway;
|
bool is_above = truncated_bits > halfway;
|
||||||
bool is_halfway = truncated_bits == halfway;
|
bool is_halfway = truncated_bits == halfway;
|
||||||
@ -215,13 +215,13 @@ is_truncated(UC const *first, UC const *last) noexcept {
|
|||||||
}
|
}
|
||||||
template <typename UC>
|
template <typename UC>
|
||||||
fastfloat_really_inline FASTFLOAT_CONSTEXPR20 bool
|
fastfloat_really_inline FASTFLOAT_CONSTEXPR20 bool
|
||||||
is_truncated(span<const UC> s) noexcept {
|
is_truncated(span<UC const> s) noexcept {
|
||||||
return is_truncated(s.ptr, s.ptr + s.len());
|
return is_truncated(s.ptr, s.ptr + s.len());
|
||||||
}
|
}
|
||||||
|
|
||||||
template <typename UC>
|
template <typename UC>
|
||||||
fastfloat_really_inline FASTFLOAT_CONSTEXPR20 void
|
fastfloat_really_inline FASTFLOAT_CONSTEXPR20 void
|
||||||
parse_eight_digits(const UC *&p, limb &value, size_t &counter,
|
parse_eight_digits(UC const *&p, limb &value, size_t &counter,
|
||||||
size_t &count) noexcept {
|
size_t &count) noexcept {
|
||||||
value = value * 100000000 + parse_eight_digits_unrolled(p);
|
value = value * 100000000 + parse_eight_digits_unrolled(p);
|
||||||
p += 8;
|
p += 8;
|
||||||
|
|||||||
@ -259,9 +259,9 @@ fastfloat_strncasecmp(UC const *actual_mixedcase, UC const *expected_lowercase,
|
|||||||
|
|
||||||
// a pointer and a length to a contiguous block of memory
|
// a pointer and a length to a contiguous block of memory
|
||||||
template <typename T> struct span {
|
template <typename T> struct span {
|
||||||
const T *ptr;
|
T const *ptr;
|
||||||
size_t length;
|
size_t length;
|
||||||
constexpr span(const T *_ptr, size_t _length) : ptr(_ptr), length(_length) {}
|
constexpr span(T const *_ptr, size_t _length) : ptr(_ptr), length(_length) {}
|
||||||
constexpr span() : ptr(nullptr), length(0) {}
|
constexpr span() : ptr(nullptr), length(0) {}
|
||||||
|
|
||||||
constexpr size_t len() const noexcept { return length; }
|
constexpr size_t len() const noexcept { return length; }
|
||||||
@ -391,10 +391,10 @@ struct adjusted_mantissa {
|
|||||||
uint64_t mantissa{0};
|
uint64_t mantissa{0};
|
||||||
int32_t power2{0}; // a negative value indicates an invalid result
|
int32_t power2{0}; // a negative value indicates an invalid result
|
||||||
adjusted_mantissa() = default;
|
adjusted_mantissa() = default;
|
||||||
constexpr bool operator==(const adjusted_mantissa &o) const {
|
constexpr bool operator==(adjusted_mantissa const &o) const {
|
||||||
return mantissa == o.mantissa && power2 == o.power2;
|
return mantissa == o.mantissa && power2 == o.power2;
|
||||||
}
|
}
|
||||||
constexpr bool operator!=(const adjusted_mantissa &o) const {
|
constexpr bool operator!=(adjusted_mantissa const &o) const {
|
||||||
return mantissa != o.mantissa || power2 != o.power2;
|
return mantissa != o.mantissa || power2 != o.power2;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|||||||
@ -95,7 +95,7 @@ fastfloat_really_inline bool rounds_to_nearest() noexcept {
|
|||||||
// asm). The value does not need to be std::numeric_limits<float>::min(), any
|
// asm). The value does not need to be std::numeric_limits<float>::min(), any
|
||||||
// small value so that 1 + x should round to 1 would do (after accounting for
|
// small value so that 1 + x should round to 1 would do (after accounting for
|
||||||
// excess precision, as in 387 instructions).
|
// excess precision, as in 387 instructions).
|
||||||
static volatile float fmin = std::numeric_limits<float>::min();
|
static float volatile fmin = std::numeric_limits<float>::min();
|
||||||
float fmini = fmin; // we copy it so that it gets loaded at most once.
|
float fmini = fmin; // we copy it so that it gets loaded at most once.
|
||||||
//
|
//
|
||||||
// Explanation:
|
// Explanation:
|
||||||
|
|||||||
@ -58,7 +58,7 @@
|
|||||||
#define fHexAndDec(v) \
|
#define fHexAndDec(v) \
|
||||||
std::hexfloat << (v) << " (" << std::defaultfloat << (v) << ")"
|
std::hexfloat << (v) << " (" << std::defaultfloat << (v) << ")"
|
||||||
|
|
||||||
const char *round_name(int d) {
|
char const *round_name(int d) {
|
||||||
switch (d) {
|
switch (d) {
|
||||||
case FE_UPWARD:
|
case FE_UPWARD:
|
||||||
return "FE_UPWARD";
|
return "FE_UPWARD";
|
||||||
@ -124,7 +124,7 @@ TEST_CASE("rounds_to_nearest") {
|
|||||||
//
|
//
|
||||||
// If this function fails, we may be left in a non-standard rounding state.
|
// If this function fails, we may be left in a non-standard rounding state.
|
||||||
//
|
//
|
||||||
static volatile float fmin = std::numeric_limits<float>::min();
|
static float volatile fmin = std::numeric_limits<float>::min();
|
||||||
fesetround(FE_UPWARD);
|
fesetround(FE_UPWARD);
|
||||||
std::cout << "FE_UPWARD: fmin + 1.0f = " << iHexAndDec(fmin + 1.0f)
|
std::cout << "FE_UPWARD: fmin + 1.0f = " << iHexAndDec(fmin + 1.0f)
|
||||||
<< " 1.0f - fmin = " << iHexAndDec(1.0f - fmin) << std::endl;
|
<< " 1.0f - fmin = " << iHexAndDec(1.0f - fmin) << std::endl;
|
||||||
@ -156,7 +156,7 @@ TEST_CASE("parse_zero") {
|
|||||||
//
|
//
|
||||||
// If this function fails, we may be left in a non-standard rounding state.
|
// If this function fails, we may be left in a non-standard rounding state.
|
||||||
//
|
//
|
||||||
const char *zero = "0";
|
char const *zero = "0";
|
||||||
uint64_t float64_parsed;
|
uint64_t float64_parsed;
|
||||||
double f = 0;
|
double f = 0;
|
||||||
::memcpy(&float64_parsed, &f, sizeof(f));
|
::memcpy(&float64_parsed, &f, sizeof(f));
|
||||||
@ -203,7 +203,7 @@ TEST_CASE("parse_negative_zero") {
|
|||||||
//
|
//
|
||||||
// If this function fails, we may be left in a non-standard rounding state.
|
// If this function fails, we may be left in a non-standard rounding state.
|
||||||
//
|
//
|
||||||
const char *negative_zero = "-0";
|
char const *negative_zero = "-0";
|
||||||
uint64_t float64_parsed;
|
uint64_t float64_parsed;
|
||||||
double f = -0.;
|
double f = -0.;
|
||||||
::memcpy(&float64_parsed, &f, sizeof(f));
|
::memcpy(&float64_parsed, &f, sizeof(f));
|
||||||
@ -292,8 +292,8 @@ bool check_file(std::string file_name) {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
// The string to parse:
|
// The string to parse:
|
||||||
const char *number_string = str.data() + 31;
|
char const *number_string = str.data() + 31;
|
||||||
const char *end_of_string = str.data() + str.size();
|
char const *end_of_string = str.data() + str.size();
|
||||||
// Parse as 32-bit float
|
// Parse as 32-bit float
|
||||||
float parsed_32;
|
float parsed_32;
|
||||||
auto fast_float_r32 =
|
auto fast_float_r32 =
|
||||||
@ -354,7 +354,7 @@ bool check_file(std::string file_name) {
|
|||||||
|
|
||||||
TEST_CASE("supplemental") {
|
TEST_CASE("supplemental") {
|
||||||
std::string path = SUPPLEMENTAL_TEST_DATA_DIR;
|
std::string path = SUPPLEMENTAL_TEST_DATA_DIR;
|
||||||
for (const auto &entry : std::filesystem::directory_iterator(path)) {
|
for (auto const &entry : std::filesystem::directory_iterator(path)) {
|
||||||
CHECK(check_file(entry.path().string()));
|
CHECK(check_file(entry.path().string()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -362,7 +362,7 @@ TEST_CASE("supplemental") {
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
TEST_CASE("leading_zeroes") {
|
TEST_CASE("leading_zeroes") {
|
||||||
constexpr const uint64_t bit = 1;
|
constexpr uint64_t const bit = 1;
|
||||||
CHECK(fast_float::leading_zeroes(bit << 0) == 63);
|
CHECK(fast_float::leading_zeroes(bit << 0) == 63);
|
||||||
CHECK(fast_float::leading_zeroes(bit << 1) == 62);
|
CHECK(fast_float::leading_zeroes(bit << 1) == 62);
|
||||||
CHECK(fast_float::leading_zeroes(bit << 2) == 61);
|
CHECK(fast_float::leading_zeroes(bit << 2) == 61);
|
||||||
@ -389,7 +389,7 @@ void test_full_multiplication(uint64_t lhs, uint64_t rhs, uint64_t expected_lo,
|
|||||||
}
|
}
|
||||||
|
|
||||||
TEST_CASE("full_multiplication") {
|
TEST_CASE("full_multiplication") {
|
||||||
constexpr const uint64_t bit = 1;
|
constexpr uint64_t const bit = 1;
|
||||||
// lhs rhs lo hi
|
// lhs rhs lo hi
|
||||||
test_full_multiplication(bit << 0, bit << 0, 1u, 0u);
|
test_full_multiplication(bit << 0, bit << 0, 1u, 0u);
|
||||||
test_full_multiplication(bit << 0, bit << 63, bit << 63, 0u);
|
test_full_multiplication(bit << 0, bit << 63, bit << 63, 0u);
|
||||||
@ -401,7 +401,7 @@ TEST_CASE("full_multiplication") {
|
|||||||
}
|
}
|
||||||
|
|
||||||
TEST_CASE("issue8") {
|
TEST_CASE("issue8") {
|
||||||
const char *s =
|
char const *s =
|
||||||
"3."
|
"3."
|
||||||
"141592653589793238462643383279502884197169399375105820974944592307816406"
|
"141592653589793238462643383279502884197169399375105820974944592307816406"
|
||||||
"286208998628034825342117067982148086513282306647093844609550582231725359"
|
"286208998628034825342117067982148086513282306647093844609550582231725359"
|
||||||
@ -428,7 +428,7 @@ TEST_CASE("issue8") {
|
|||||||
}
|
}
|
||||||
|
|
||||||
TEST_CASE("check_behavior") {
|
TEST_CASE("check_behavior") {
|
||||||
const std::string input = "abc";
|
std::string const input = "abc";
|
||||||
double result;
|
double result;
|
||||||
auto answer =
|
auto answer =
|
||||||
fast_float::from_chars(input.data(), input.data() + input.size(), result);
|
fast_float::from_chars(input.data(), input.data() + input.size(), result);
|
||||||
@ -442,7 +442,7 @@ TEST_CASE("decimal_point_parsing") {
|
|||||||
double result;
|
double result;
|
||||||
fast_float::parse_options options{};
|
fast_float::parse_options options{};
|
||||||
{
|
{
|
||||||
const std::string input = "1,25";
|
std::string const input = "1,25";
|
||||||
auto answer = fast_float::from_chars_advanced(
|
auto answer = fast_float::from_chars_advanced(
|
||||||
input.data(), input.data() + input.size(), result, options);
|
input.data(), input.data() + input.size(), result, options);
|
||||||
CHECK_MESSAGE(answer.ec == std::errc(), "expected parse success");
|
CHECK_MESSAGE(answer.ec == std::errc(), "expected parse success");
|
||||||
@ -459,7 +459,7 @@ TEST_CASE("decimal_point_parsing") {
|
|||||||
CHECK_EQ(result, 1.25);
|
CHECK_EQ(result, 1.25);
|
||||||
}
|
}
|
||||||
{
|
{
|
||||||
const std::string input = "1.25";
|
std::string const input = "1.25";
|
||||||
auto answer = fast_float::from_chars_advanced(
|
auto answer = fast_float::from_chars_advanced(
|
||||||
input.data(), input.data() + input.size(), result, options);
|
input.data(), input.data() + input.size(), result, options);
|
||||||
CHECK_MESSAGE(answer.ec == std::errc(), "expected parse success");
|
CHECK_MESSAGE(answer.ec == std::errc(), "expected parse success");
|
||||||
@ -478,7 +478,7 @@ TEST_CASE("decimal_point_parsing") {
|
|||||||
}
|
}
|
||||||
|
|
||||||
TEST_CASE("issue19") {
|
TEST_CASE("issue19") {
|
||||||
const std::string input = "234532.3426362,7869234.9823,324562.645";
|
std::string const input = "234532.3426362,7869234.9823,324562.645";
|
||||||
double result;
|
double result;
|
||||||
auto answer =
|
auto answer =
|
||||||
fast_float::from_chars(input.data(), input.data() + input.size(), result);
|
fast_float::from_chars(input.data(), input.data() + input.size(), result);
|
||||||
@ -512,7 +512,7 @@ TEST_CASE("issue19") {
|
|||||||
}
|
}
|
||||||
|
|
||||||
TEST_CASE("issue19") {
|
TEST_CASE("issue19") {
|
||||||
const std::string input = "3.14e";
|
std::string const input = "3.14e";
|
||||||
double result;
|
double result;
|
||||||
auto answer =
|
auto answer =
|
||||||
fast_float::from_chars(input.data(), input.data() + input.size(), result);
|
fast_float::from_chars(input.data(), input.data() + input.size(), result);
|
||||||
@ -545,7 +545,7 @@ TEST_CASE("scientific_only") {
|
|||||||
}
|
}
|
||||||
|
|
||||||
TEST_CASE("test_fixed_only") {
|
TEST_CASE("test_fixed_only") {
|
||||||
const std::string input = "3.14e10";
|
std::string const input = "3.14e10";
|
||||||
double result;
|
double result;
|
||||||
auto answer =
|
auto answer =
|
||||||
fast_float::from_chars(input.data(), input.data() + input.size(), result,
|
fast_float::from_chars(input.data(), input.data() + input.size(), result,
|
||||||
@ -558,7 +558,7 @@ TEST_CASE("test_fixed_only") {
|
|||||||
<< (answer.ptr - input.data()) << " characters");
|
<< (answer.ptr - input.data()) << " characters");
|
||||||
}
|
}
|
||||||
|
|
||||||
static const double testing_power_of_ten[] = {
|
static double const testing_power_of_ten[] = {
|
||||||
1e-323, 1e-322, 1e-321, 1e-320, 1e-319, 1e-318, 1e-317, 1e-316, 1e-315,
|
1e-323, 1e-322, 1e-321, 1e-320, 1e-319, 1e-318, 1e-317, 1e-316, 1e-315,
|
||||||
1e-314, 1e-313, 1e-312, 1e-311, 1e-310, 1e-309, 1e-308,
|
1e-314, 1e-313, 1e-312, 1e-311, 1e-310, 1e-309, 1e-308,
|
||||||
|
|
||||||
@ -719,7 +719,7 @@ constexpr void check_basic_test_result(stringtype str, result_type result,
|
|||||||
if constexpr (diag == Diag::runtime) { \
|
if constexpr (diag == Diag::runtime) { \
|
||||||
CHECK_EQ(__VA_ARGS__); \
|
CHECK_EQ(__VA_ARGS__); \
|
||||||
} else { \
|
} else { \
|
||||||
if ([](const auto &lhs, const auto &rhs) { \
|
if ([](auto const &lhs, auto const &rhs) { \
|
||||||
return lhs != rhs; \
|
return lhs != rhs; \
|
||||||
}(__VA_ARGS__)) { \
|
}(__VA_ARGS__)) { \
|
||||||
ComptimeDiag::error_not_equal(); \
|
ComptimeDiag::error_not_equal(); \
|
||||||
@ -731,7 +731,7 @@ constexpr void check_basic_test_result(stringtype str, result_type result,
|
|||||||
if (fast_float::cpp20_and_in_constexpr()) {
|
if (fast_float::cpp20_and_in_constexpr()) {
|
||||||
using equiv_int = std::make_signed_t<
|
using equiv_int = std::make_signed_t<
|
||||||
typename fast_float::binary_format<double>::equiv_uint>;
|
typename fast_float::binary_format<double>::equiv_uint>;
|
||||||
const auto i = std::bit_cast<equiv_int>(y);
|
auto const i = std::bit_cast<equiv_int>(y);
|
||||||
if (i < 0) {
|
if (i < 0) {
|
||||||
return -x;
|
return -x;
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
#include "fast_float/fast_float.h"
|
#include "fast_float/fast_float.h"
|
||||||
|
|
||||||
double get1(const char *input) {
|
double get1(char const *input) {
|
||||||
double result_value;
|
double result_value;
|
||||||
auto result =
|
auto result =
|
||||||
fast_float::from_chars(input, input + strlen(input), result_value);
|
fast_float::from_chars(input, input + strlen(input), result_value);
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
#include "fast_float/fast_float.h"
|
#include "fast_float/fast_float.h"
|
||||||
|
|
||||||
double get10(const char *input) {
|
double get10(char const *input) {
|
||||||
double result_value;
|
double result_value;
|
||||||
auto result =
|
auto result =
|
||||||
fast_float::from_chars(input, input + strlen(input), result_value);
|
fast_float::from_chars(input, input + strlen(input), result_value);
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
#include "fast_float/fast_float.h"
|
#include "fast_float/fast_float.h"
|
||||||
|
|
||||||
double get2(const char *input) {
|
double get2(char const *input) {
|
||||||
double result_value;
|
double result_value;
|
||||||
auto result =
|
auto result =
|
||||||
fast_float::from_chars(input, input + strlen(input), result_value);
|
fast_float::from_chars(input, input + strlen(input), result_value);
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
#include "fast_float/fast_float.h"
|
#include "fast_float/fast_float.h"
|
||||||
|
|
||||||
double get3(const char *input) {
|
double get3(char const *input) {
|
||||||
double result_value;
|
double result_value;
|
||||||
auto result =
|
auto result =
|
||||||
fast_float::from_chars(input, input + strlen(input), result_value);
|
fast_float::from_chars(input, input + strlen(input), result_value);
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
#include "fast_float/fast_float.h"
|
#include "fast_float/fast_float.h"
|
||||||
|
|
||||||
double get4(const char *input) {
|
double get4(char const *input) {
|
||||||
double result_value;
|
double result_value;
|
||||||
auto result =
|
auto result =
|
||||||
fast_float::from_chars(input, input + strlen(input), result_value);
|
fast_float::from_chars(input, input + strlen(input), result_value);
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
#include "fast_float/fast_float.h"
|
#include "fast_float/fast_float.h"
|
||||||
|
|
||||||
double get5(const char *input) {
|
double get5(char const *input) {
|
||||||
double result_value;
|
double result_value;
|
||||||
auto result =
|
auto result =
|
||||||
fast_float::from_chars(input, input + strlen(input), result_value);
|
fast_float::from_chars(input, input + strlen(input), result_value);
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
#include "fast_float/fast_float.h"
|
#include "fast_float/fast_float.h"
|
||||||
|
|
||||||
double get6(const char *input) {
|
double get6(char const *input) {
|
||||||
double result_value;
|
double result_value;
|
||||||
auto result =
|
auto result =
|
||||||
fast_float::from_chars(input, input + strlen(input), result_value);
|
fast_float::from_chars(input, input + strlen(input), result_value);
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
#include "fast_float/fast_float.h"
|
#include "fast_float/fast_float.h"
|
||||||
|
|
||||||
double get7(const char *input) {
|
double get7(char const *input) {
|
||||||
double result_value;
|
double result_value;
|
||||||
auto result =
|
auto result =
|
||||||
fast_float::from_chars(input, input + strlen(input), result_value);
|
fast_float::from_chars(input, input + strlen(input), result_value);
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
#include "fast_float/fast_float.h"
|
#include "fast_float/fast_float.h"
|
||||||
|
|
||||||
double get8(const char *input) {
|
double get8(char const *input) {
|
||||||
double result_value;
|
double result_value;
|
||||||
auto result =
|
auto result =
|
||||||
fast_float::from_chars(input, input + strlen(input), result_value);
|
fast_float::from_chars(input, input + strlen(input), result_value);
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
#include "fast_float/fast_float.h"
|
#include "fast_float/fast_float.h"
|
||||||
|
|
||||||
double get9(const char *input) {
|
double get9(char const *input) {
|
||||||
double result_value;
|
double result_value;
|
||||||
auto result =
|
auto result =
|
||||||
fast_float::from_chars(input, input + strlen(input), result_value);
|
fast_float::from_chars(input, input + strlen(input), result_value);
|
||||||
|
|||||||
@ -1,15 +1,15 @@
|
|||||||
|
|
||||||
|
|
||||||
double get1(const char *input);
|
double get1(char const *input);
|
||||||
double get2(const char *input);
|
double get2(char const *input);
|
||||||
double get3(const char *input);
|
double get3(char const *input);
|
||||||
double get4(const char *input);
|
double get4(char const *input);
|
||||||
double get5(const char *input);
|
double get5(char const *input);
|
||||||
double get6(const char *input);
|
double get6(char const *input);
|
||||||
double get7(const char *input);
|
double get7(char const *input);
|
||||||
double get8(const char *input);
|
double get8(char const *input);
|
||||||
double get9(const char *input);
|
double get9(char const *input);
|
||||||
double get10(const char *input);
|
double get10(char const *input);
|
||||||
|
|
||||||
int main(int arg, char **argv) {
|
int main(int arg, char **argv) {
|
||||||
double x = get1(argv[0]) + get2(argv[0]) + get3(argv[0]) + get4(argv[0]) +
|
double x = get1(argv[0]) + get2(argv[0]) + get3(argv[0]) + get4(argv[0]) +
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
#include "fast_float/fast_float.h"
|
#include "fast_float/fast_float.h"
|
||||||
|
|
||||||
double get(const char *input) {
|
double get(char const *input) {
|
||||||
double result_value;
|
double result_value;
|
||||||
auto result =
|
auto result =
|
||||||
fast_float::from_chars(input, input + strlen(input), result_value);
|
fast_float::from_chars(input, input + strlen(input), result_value);
|
||||||
|
|||||||
@ -5,7 +5,7 @@
|
|||||||
#include <system_error>
|
#include <system_error>
|
||||||
|
|
||||||
int main() {
|
int main() {
|
||||||
const std::string input = "3,1416 xyz ";
|
std::string const input = "3,1416 xyz ";
|
||||||
double result;
|
double result;
|
||||||
fast_float::parse_options options{fast_float::chars_format::general, ','};
|
fast_float::parse_options options{fast_float::chars_format::general, ','};
|
||||||
auto answer = fast_float::from_chars_advanced(
|
auto answer = fast_float::from_chars_advanced(
|
||||||
|
|||||||
@ -5,7 +5,7 @@
|
|||||||
#include <system_error>
|
#include <system_error>
|
||||||
|
|
||||||
bool many() {
|
bool many() {
|
||||||
const std::string input = "234532.3426362,7869234.9823,324562.645";
|
std::string const input = "234532.3426362,7869234.9823,324562.645";
|
||||||
double result;
|
double result;
|
||||||
auto answer =
|
auto answer =
|
||||||
fast_float::from_chars(input.data(), input.data() + input.size(), result);
|
fast_float::from_chars(input.data(), input.data() + input.size(), result);
|
||||||
@ -41,10 +41,10 @@ bool many() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void many_loop() {
|
void many_loop() {
|
||||||
const std::string input = "234532.3426362,7869234.9823,324562.645";
|
std::string const input = "234532.3426362,7869234.9823,324562.645";
|
||||||
double result;
|
double result;
|
||||||
const char *pointer = input.data();
|
char const *pointer = input.data();
|
||||||
const char *end_pointer = input.data() + input.size();
|
char const *end_pointer = input.data() + input.size();
|
||||||
|
|
||||||
while (pointer < end_pointer) {
|
while (pointer < end_pointer) {
|
||||||
auto answer = fast_float::from_chars(pointer, end_pointer, result);
|
auto answer = fast_float::from_chars(pointer, end_pointer, result);
|
||||||
@ -112,7 +112,7 @@ bool large() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
int main() {
|
int main() {
|
||||||
const std::string input = "3.1416 xyz ";
|
std::string const input = "3.1416 xyz ";
|
||||||
double result;
|
double result;
|
||||||
auto answer =
|
auto answer =
|
||||||
fast_float::from_chars(input.data(), input.data() + input.size(), result);
|
fast_float::from_chars(input.data(), input.data() + input.size(), result);
|
||||||
|
|||||||
@ -27,7 +27,7 @@ void allvalues() {
|
|||||||
memcpy(&v, &word, sizeof(v));
|
memcpy(&v, &word, sizeof(v));
|
||||||
|
|
||||||
{
|
{
|
||||||
const char *string_end = to_string(v, buffer);
|
char const *string_end = to_string(v, buffer);
|
||||||
float result_value;
|
float result_value;
|
||||||
auto result = fast_float::from_chars(buffer, string_end, result_value);
|
auto result = fast_float::from_chars(buffer, string_end, result_value);
|
||||||
// Starting with version 4.0 for fast_float, we return result_out_of_range
|
// Starting with version 4.0 for fast_float, we return result_out_of_range
|
||||||
|
|||||||
@ -58,7 +58,7 @@ void all_32bit_values() {
|
|||||||
double v = v32;
|
double v = v32;
|
||||||
|
|
||||||
{
|
{
|
||||||
const char *string_end = to_string(v, buffer);
|
char const *string_end = to_string(v, buffer);
|
||||||
std::string s(buffer, size_t(string_end - buffer));
|
std::string s(buffer, size_t(string_end - buffer));
|
||||||
if (!basic_test_64bit(s, v)) {
|
if (!basic_test_64bit(s, v)) {
|
||||||
return;
|
return;
|
||||||
|
|||||||
@ -15,7 +15,7 @@
|
|||||||
#include <locale>
|
#include <locale>
|
||||||
#include <sstream>
|
#include <sstream>
|
||||||
// workaround for CYGWIN
|
// workaround for CYGWIN
|
||||||
double cygwin_strtod_l(const char *start, char **end) {
|
double cygwin_strtod_l(char const *start, char **end) {
|
||||||
double d;
|
double d;
|
||||||
std::stringstream ss;
|
std::stringstream ss;
|
||||||
ss.imbue(std::locale::classic());
|
ss.imbue(std::locale::classic());
|
||||||
@ -31,7 +31,7 @@ double cygwin_strtod_l(const char *start, char **end) {
|
|||||||
*end = const_cast<char *>(start) + nread;
|
*end = const_cast<char *>(start) + nread;
|
||||||
return d;
|
return d;
|
||||||
}
|
}
|
||||||
float cygwin_strtof_l(const char *start, char **end) {
|
float cygwin_strtof_l(char const *start, char **end) {
|
||||||
float d;
|
float d;
|
||||||
std::stringstream ss;
|
std::stringstream ss;
|
||||||
ss.imbue(std::locale::classic());
|
ss.imbue(std::locale::classic());
|
||||||
@ -55,7 +55,7 @@ template <typename T> char *to_string(T d, char *buffer) {
|
|||||||
return buffer + written;
|
return buffer + written;
|
||||||
}
|
}
|
||||||
|
|
||||||
void strtof_from_string(const char *st, float &d) {
|
void strtof_from_string(char const *st, float &d) {
|
||||||
char *pr = (char *)st;
|
char *pr = (char *)st;
|
||||||
#if defined(__CYGWIN__) || defined(__MINGW32__) || defined(__MINGW64__) || \
|
#if defined(__CYGWIN__) || defined(__MINGW32__) || defined(__MINGW64__) || \
|
||||||
defined(sun) || defined(__sun)
|
defined(sun) || defined(__sun)
|
||||||
@ -97,7 +97,7 @@ bool allvalues() {
|
|||||||
double midv{v1 + (v2 - v1) / 2};
|
double midv{v1 + (v2 - v1) / 2};
|
||||||
float expected_midv = float(midv);
|
float expected_midv = float(midv);
|
||||||
|
|
||||||
const char *string_end = to_string(midv, buffer);
|
char const *string_end = to_string(midv, buffer);
|
||||||
float str_answer;
|
float str_answer;
|
||||||
strtof_from_string(buffer, str_answer);
|
strtof_from_string(buffer, str_answer);
|
||||||
|
|
||||||
|
|||||||
@ -46,12 +46,12 @@ ignores all zeroes in front of valid number after converted from base
|
|||||||
|
|
||||||
int main() {
|
int main() {
|
||||||
// int basic test
|
// int basic test
|
||||||
const std::vector<int> int_basic_test_expected{0, 10, -40, 1001, 9};
|
std::vector<int> const int_basic_test_expected{0, 10, -40, 1001, 9};
|
||||||
const std::vector<std::string_view> int_basic_test{"0", "10 ", "-40",
|
std::vector<std::string_view> const int_basic_test{"0", "10 ", "-40",
|
||||||
"1001 with text", "9.999"};
|
"1001 with text", "9.999"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < int_basic_test.size(); ++i) {
|
for (std::size_t i = 0; i < int_basic_test.size(); ++i) {
|
||||||
const auto f = int_basic_test[i];
|
auto const f = int_basic_test[i];
|
||||||
int result;
|
int result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
||||||
|
|
||||||
@ -75,12 +75,12 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// unsigned basic test
|
// unsigned basic test
|
||||||
const std::vector<unsigned> unsigned_basic_test_expected{0, 10, 1001, 9};
|
std::vector<unsigned> const unsigned_basic_test_expected{0, 10, 1001, 9};
|
||||||
const std::vector<std::string_view> unsigned_basic_test{
|
std::vector<std::string_view> const unsigned_basic_test{
|
||||||
"0", "10 ", "1001 with text", "9.999"};
|
"0", "10 ", "1001 with text", "9.999"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < unsigned_basic_test.size(); ++i) {
|
for (std::size_t i = 0; i < unsigned_basic_test.size(); ++i) {
|
||||||
const auto &f = unsigned_basic_test[i];
|
auto const &f = unsigned_basic_test[i];
|
||||||
unsigned result;
|
unsigned result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
||||||
if (answer.ec != std::errc()) {
|
if (answer.ec != std::errc()) {
|
||||||
@ -96,11 +96,11 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// int invalid error test
|
// int invalid error test
|
||||||
const std::vector<std::string_view> int_invalid_argument_test{
|
std::vector<std::string_view> const int_invalid_argument_test{
|
||||||
"text", "text with 1002", "+50", " 50"};
|
"text", "text with 1002", "+50", " 50"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < int_invalid_argument_test.size(); ++i) {
|
for (std::size_t i = 0; i < int_invalid_argument_test.size(); ++i) {
|
||||||
const auto &f = int_invalid_argument_test[i];
|
auto const &f = int_invalid_argument_test[i];
|
||||||
int result;
|
int result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
||||||
if (answer.ec != std::errc::invalid_argument) {
|
if (answer.ec != std::errc::invalid_argument) {
|
||||||
@ -111,11 +111,11 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// unsigned invalid error test
|
// unsigned invalid error test
|
||||||
const std::vector<std::string_view> unsigned_invalid_argument_test{
|
std::vector<std::string_view> const unsigned_invalid_argument_test{
|
||||||
"text", "text with 1002", "+50", " 50", "-50"};
|
"text", "text with 1002", "+50", " 50", "-50"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < unsigned_invalid_argument_test.size(); ++i) {
|
for (std::size_t i = 0; i < unsigned_invalid_argument_test.size(); ++i) {
|
||||||
const auto &f = unsigned_invalid_argument_test[i];
|
auto const &f = unsigned_invalid_argument_test[i];
|
||||||
unsigned result;
|
unsigned result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
||||||
if (answer.ec != std::errc::invalid_argument) {
|
if (answer.ec != std::errc::invalid_argument) {
|
||||||
@ -126,11 +126,11 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// int out of range error test #1 (8 bit)
|
// int out of range error test #1 (8 bit)
|
||||||
const std::vector<std::string_view> int_out_of_range_test_1{
|
std::vector<std::string_view> const int_out_of_range_test_1{
|
||||||
"2000000000000000000000", "128", "-129"};
|
"2000000000000000000000", "128", "-129"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < int_out_of_range_test_1.size(); ++i) {
|
for (std::size_t i = 0; i < int_out_of_range_test_1.size(); ++i) {
|
||||||
const auto &f = int_out_of_range_test_1[i];
|
auto const &f = int_out_of_range_test_1[i];
|
||||||
int8_t result;
|
int8_t result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
||||||
if (answer.ec != std::errc::result_out_of_range) {
|
if (answer.ec != std::errc::result_out_of_range) {
|
||||||
@ -141,11 +141,11 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// int out of range error test #2 (16 bit)
|
// int out of range error test #2 (16 bit)
|
||||||
const std::vector<std::string_view> int_out_of_range_test_2{
|
std::vector<std::string_view> const int_out_of_range_test_2{
|
||||||
"2000000000000000000000", "32768", "-32769"};
|
"2000000000000000000000", "32768", "-32769"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < int_out_of_range_test_2.size(); ++i) {
|
for (std::size_t i = 0; i < int_out_of_range_test_2.size(); ++i) {
|
||||||
const auto &f = int_out_of_range_test_2[i];
|
auto const &f = int_out_of_range_test_2[i];
|
||||||
int16_t result;
|
int16_t result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
||||||
if (answer.ec != std::errc::result_out_of_range) {
|
if (answer.ec != std::errc::result_out_of_range) {
|
||||||
@ -156,11 +156,11 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// int out of range error test #3 (32 bit)
|
// int out of range error test #3 (32 bit)
|
||||||
const std::vector<std::string_view> int_out_of_range_test_3{
|
std::vector<std::string_view> const int_out_of_range_test_3{
|
||||||
"2000000000000000000000", "2147483648", "-2147483649"};
|
"2000000000000000000000", "2147483648", "-2147483649"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < int_out_of_range_test_3.size(); ++i) {
|
for (std::size_t i = 0; i < int_out_of_range_test_3.size(); ++i) {
|
||||||
const auto &f = int_out_of_range_test_3[i];
|
auto const &f = int_out_of_range_test_3[i];
|
||||||
int32_t result;
|
int32_t result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
||||||
if (answer.ec != std::errc::result_out_of_range) {
|
if (answer.ec != std::errc::result_out_of_range) {
|
||||||
@ -171,11 +171,11 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// int out of range error test #4 (64 bit)
|
// int out of range error test #4 (64 bit)
|
||||||
const std::vector<std::string_view> int_out_of_range_test_4{
|
std::vector<std::string_view> const int_out_of_range_test_4{
|
||||||
"2000000000000000000000", "9223372036854775808", "-9223372036854775809"};
|
"2000000000000000000000", "9223372036854775808", "-9223372036854775809"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < int_out_of_range_test_4.size(); ++i) {
|
for (std::size_t i = 0; i < int_out_of_range_test_4.size(); ++i) {
|
||||||
const auto &f = int_out_of_range_test_4[i];
|
auto const &f = int_out_of_range_test_4[i];
|
||||||
int64_t result;
|
int64_t result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
||||||
if (answer.ec != std::errc::result_out_of_range) {
|
if (answer.ec != std::errc::result_out_of_range) {
|
||||||
@ -186,11 +186,11 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// unsigned out of range error test #1 (8 bit)
|
// unsigned out of range error test #1 (8 bit)
|
||||||
const std::vector<std::string_view> unsigned_out_of_range_test_1{
|
std::vector<std::string_view> const unsigned_out_of_range_test_1{
|
||||||
"2000000000000000000000", "256"};
|
"2000000000000000000000", "256"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < unsigned_out_of_range_test_1.size(); ++i) {
|
for (std::size_t i = 0; i < unsigned_out_of_range_test_1.size(); ++i) {
|
||||||
const auto &f = unsigned_out_of_range_test_1[i];
|
auto const &f = unsigned_out_of_range_test_1[i];
|
||||||
uint8_t result;
|
uint8_t result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
||||||
if (answer.ec != std::errc::result_out_of_range) {
|
if (answer.ec != std::errc::result_out_of_range) {
|
||||||
@ -201,11 +201,11 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// unsigned out of range error test #2 (16 bit)
|
// unsigned out of range error test #2 (16 bit)
|
||||||
const std::vector<std::string_view> unsigned_out_of_range_test_2{
|
std::vector<std::string_view> const unsigned_out_of_range_test_2{
|
||||||
"2000000000000000000000", "65536"};
|
"2000000000000000000000", "65536"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < unsigned_out_of_range_test_2.size(); ++i) {
|
for (std::size_t i = 0; i < unsigned_out_of_range_test_2.size(); ++i) {
|
||||||
const auto &f = unsigned_out_of_range_test_2[i];
|
auto const &f = unsigned_out_of_range_test_2[i];
|
||||||
uint16_t result;
|
uint16_t result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
||||||
if (answer.ec != std::errc::result_out_of_range) {
|
if (answer.ec != std::errc::result_out_of_range) {
|
||||||
@ -216,11 +216,11 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// unsigned out of range error test #3 (32 bit)
|
// unsigned out of range error test #3 (32 bit)
|
||||||
const std::vector<std::string_view> unsigned_out_of_range_test_3{
|
std::vector<std::string_view> const unsigned_out_of_range_test_3{
|
||||||
"2000000000000000000000", "4294967296"};
|
"2000000000000000000000", "4294967296"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < unsigned_out_of_range_test_3.size(); ++i) {
|
for (std::size_t i = 0; i < unsigned_out_of_range_test_3.size(); ++i) {
|
||||||
const auto &f = unsigned_out_of_range_test_3[i];
|
auto const &f = unsigned_out_of_range_test_3[i];
|
||||||
uint32_t result;
|
uint32_t result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
||||||
if (answer.ec != std::errc::result_out_of_range) {
|
if (answer.ec != std::errc::result_out_of_range) {
|
||||||
@ -231,11 +231,11 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// unsigned out of range error test #4 (64 bit)
|
// unsigned out of range error test #4 (64 bit)
|
||||||
const std::vector<std::string_view> unsigned_out_of_range_test_4{
|
std::vector<std::string_view> const unsigned_out_of_range_test_4{
|
||||||
"2000000000000000000000", "18446744073709551616"};
|
"2000000000000000000000", "18446744073709551616"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < unsigned_out_of_range_test_4.size(); ++i) {
|
for (std::size_t i = 0; i < unsigned_out_of_range_test_4.size(); ++i) {
|
||||||
const auto &f = unsigned_out_of_range_test_4[i];
|
auto const &f = unsigned_out_of_range_test_4[i];
|
||||||
uint64_t result;
|
uint64_t result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
||||||
if (answer.ec != std::errc::result_out_of_range) {
|
if (answer.ec != std::errc::result_out_of_range) {
|
||||||
@ -246,10 +246,10 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// int pointer test #1 (only numbers)
|
// int pointer test #1 (only numbers)
|
||||||
const std::vector<std::string_view> int_pointer_test_1{"0", "010", "-40"};
|
std::vector<std::string_view> const int_pointer_test_1{"0", "010", "-40"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < int_pointer_test_1.size(); ++i) {
|
for (std::size_t i = 0; i < int_pointer_test_1.size(); ++i) {
|
||||||
const auto &f = int_pointer_test_1[i];
|
auto const &f = int_pointer_test_1[i];
|
||||||
int result;
|
int result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
||||||
if (answer.ec != std::errc()) {
|
if (answer.ec != std::errc()) {
|
||||||
@ -264,9 +264,9 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// int pointer test #2 (string behind numbers)
|
// int pointer test #2 (string behind numbers)
|
||||||
const std::string_view int_pointer_test_2 = "1001 with text";
|
std::string_view const int_pointer_test_2 = "1001 with text";
|
||||||
|
|
||||||
const auto &f2 = int_pointer_test_2;
|
auto const &f2 = int_pointer_test_2;
|
||||||
int result2;
|
int result2;
|
||||||
auto answer2 =
|
auto answer2 =
|
||||||
fast_float::from_chars(f2.data(), f2.data() + f2.size(), result2);
|
fast_float::from_chars(f2.data(), f2.data() + f2.size(), result2);
|
||||||
@ -277,9 +277,9 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// int pointer test #3 (string with newline behind numbers)
|
// int pointer test #3 (string with newline behind numbers)
|
||||||
const std::string_view int_pointer_test_3 = "1001 with text\n";
|
std::string_view const int_pointer_test_3 = "1001 with text\n";
|
||||||
|
|
||||||
const auto &f3 = int_pointer_test_3;
|
auto const &f3 = int_pointer_test_3;
|
||||||
int result3;
|
int result3;
|
||||||
auto answer3 =
|
auto answer3 =
|
||||||
fast_float::from_chars(f3.data(), f3.data() + f3.size(), result3);
|
fast_float::from_chars(f3.data(), f3.data() + f3.size(), result3);
|
||||||
@ -290,9 +290,9 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// int pointer test #4 (float)
|
// int pointer test #4 (float)
|
||||||
const std::string_view int_pointer_test_4 = "9.999";
|
std::string_view const int_pointer_test_4 = "9.999";
|
||||||
|
|
||||||
const auto &f4 = int_pointer_test_4;
|
auto const &f4 = int_pointer_test_4;
|
||||||
int result4;
|
int result4;
|
||||||
auto answer4 =
|
auto answer4 =
|
||||||
fast_float::from_chars(f4.data(), f4.data() + f4.size(), result4);
|
fast_float::from_chars(f4.data(), f4.data() + f4.size(), result4);
|
||||||
@ -303,9 +303,9 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// int pointer test #5 (invalid int)
|
// int pointer test #5 (invalid int)
|
||||||
const std::string_view int_pointer_test_5 = "+50";
|
std::string_view const int_pointer_test_5 = "+50";
|
||||||
|
|
||||||
const auto &f5 = int_pointer_test_5;
|
auto const &f5 = int_pointer_test_5;
|
||||||
int result5;
|
int result5;
|
||||||
auto answer5 =
|
auto answer5 =
|
||||||
fast_float::from_chars(f5.data(), f5.data() + f5.size(), result5);
|
fast_float::from_chars(f5.data(), f5.data() + f5.size(), result5);
|
||||||
@ -316,9 +316,9 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// unsigned pointer test #2 (string behind numbers)
|
// unsigned pointer test #2 (string behind numbers)
|
||||||
const std::string_view unsigned_pointer_test_1 = "1001 with text";
|
std::string_view const unsigned_pointer_test_1 = "1001 with text";
|
||||||
|
|
||||||
const auto &f6 = unsigned_pointer_test_1;
|
auto const &f6 = unsigned_pointer_test_1;
|
||||||
unsigned result6;
|
unsigned result6;
|
||||||
auto answer6 =
|
auto answer6 =
|
||||||
fast_float::from_chars(f6.data(), f6.data() + f6.size(), result6);
|
fast_float::from_chars(f6.data(), f6.data() + f6.size(), result6);
|
||||||
@ -329,9 +329,9 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// unsigned pointer test #2 (invalid unsigned)
|
// unsigned pointer test #2 (invalid unsigned)
|
||||||
const std::string_view unsigned_pointer_test_2 = "-50";
|
std::string_view const unsigned_pointer_test_2 = "-50";
|
||||||
|
|
||||||
const auto &f7 = unsigned_pointer_test_2;
|
auto const &f7 = unsigned_pointer_test_2;
|
||||||
unsigned result7;
|
unsigned result7;
|
||||||
auto answer7 =
|
auto answer7 =
|
||||||
fast_float::from_chars(f7.data(), f7.data() + f7.size(), result7);
|
fast_float::from_chars(f7.data(), f7.data() + f7.size(), result7);
|
||||||
@ -342,12 +342,12 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// int base 2 test
|
// int base 2 test
|
||||||
const std::vector<int> int_base_2_test_expected{0, 1, 4, 2, -1};
|
std::vector<int> const int_base_2_test_expected{0, 1, 4, 2, -1};
|
||||||
const std::vector<std::string_view> int_base_2_test{"0", "1", "100", "010",
|
std::vector<std::string_view> const int_base_2_test{"0", "1", "100", "010",
|
||||||
"-1"};
|
"-1"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < int_base_2_test.size(); ++i) {
|
for (std::size_t i = 0; i < int_base_2_test.size(); ++i) {
|
||||||
const auto f = int_base_2_test[i];
|
auto const f = int_base_2_test[i];
|
||||||
int result;
|
int result;
|
||||||
auto answer =
|
auto answer =
|
||||||
fast_float::from_chars(f.data(), f.data() + f.size(), result, 2);
|
fast_float::from_chars(f.data(), f.data() + f.size(), result, 2);
|
||||||
@ -363,12 +363,12 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// unsigned base 2 test
|
// unsigned base 2 test
|
||||||
const std::vector<unsigned> unsigned_base_2_test_expected{0, 1, 4, 2};
|
std::vector<unsigned> const unsigned_base_2_test_expected{0, 1, 4, 2};
|
||||||
const std::vector<std::string_view> unsigned_base_2_test{"0", "1", "100",
|
std::vector<std::string_view> const unsigned_base_2_test{"0", "1", "100",
|
||||||
"010"};
|
"010"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < unsigned_base_2_test.size(); ++i) {
|
for (std::size_t i = 0; i < unsigned_base_2_test.size(); ++i) {
|
||||||
const auto &f = unsigned_base_2_test[i];
|
auto const &f = unsigned_base_2_test[i];
|
||||||
unsigned result;
|
unsigned result;
|
||||||
auto answer =
|
auto answer =
|
||||||
fast_float::from_chars(f.data(), f.data() + f.size(), result, 2);
|
fast_float::from_chars(f.data(), f.data() + f.size(), result, 2);
|
||||||
@ -384,11 +384,11 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// int invalid error base 2 test
|
// int invalid error base 2 test
|
||||||
const std::vector<std::string_view> int_invalid_argument_base_2_test{"2", "A",
|
std::vector<std::string_view> const int_invalid_argument_base_2_test{"2", "A",
|
||||||
"-2"};
|
"-2"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < int_invalid_argument_base_2_test.size(); ++i) {
|
for (std::size_t i = 0; i < int_invalid_argument_base_2_test.size(); ++i) {
|
||||||
const auto &f = int_invalid_argument_base_2_test[i];
|
auto const &f = int_invalid_argument_base_2_test[i];
|
||||||
int result;
|
int result;
|
||||||
auto answer =
|
auto answer =
|
||||||
fast_float::from_chars(f.data(), f.data() + f.size(), result, 2);
|
fast_float::from_chars(f.data(), f.data() + f.size(), result, 2);
|
||||||
@ -400,12 +400,12 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// unsigned invalid error base 2 test
|
// unsigned invalid error base 2 test
|
||||||
const std::vector<std::string_view> unsigned_invalid_argument_base_2_test{
|
std::vector<std::string_view> const unsigned_invalid_argument_base_2_test{
|
||||||
"2", "A", "-1", "-2"};
|
"2", "A", "-1", "-2"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < unsigned_invalid_argument_base_2_test.size();
|
for (std::size_t i = 0; i < unsigned_invalid_argument_base_2_test.size();
|
||||||
++i) {
|
++i) {
|
||||||
const auto &f = unsigned_invalid_argument_base_2_test[i];
|
auto const &f = unsigned_invalid_argument_base_2_test[i];
|
||||||
unsigned result;
|
unsigned result;
|
||||||
auto answer =
|
auto answer =
|
||||||
fast_float::from_chars(f.data(), f.data() + f.size(), result, 2);
|
fast_float::from_chars(f.data(), f.data() + f.size(), result, 2);
|
||||||
@ -417,12 +417,12 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// octal test
|
// octal test
|
||||||
const std::vector<int> base_octal_test_expected{0, 1, 7, 8, 9};
|
std::vector<int> const base_octal_test_expected{0, 1, 7, 8, 9};
|
||||||
const std::vector<std::string_view> base_octal_test{"0", "1", "07", "010",
|
std::vector<std::string_view> const base_octal_test{"0", "1", "07", "010",
|
||||||
"0011"};
|
"0011"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < base_octal_test.size(); ++i) {
|
for (std::size_t i = 0; i < base_octal_test.size(); ++i) {
|
||||||
const auto &f = base_octal_test[i];
|
auto const &f = base_octal_test[i];
|
||||||
int result;
|
int result;
|
||||||
auto answer =
|
auto answer =
|
||||||
fast_float::from_chars(f.data(), f.data() + f.size(), result, 8);
|
fast_float::from_chars(f.data(), f.data() + f.size(), result, 8);
|
||||||
@ -438,12 +438,12 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// hex test
|
// hex test
|
||||||
const std::vector<int> base_hex_test_expected{0, 1, 15, 31, 0, 16};
|
std::vector<int> const base_hex_test_expected{0, 1, 15, 31, 0, 16};
|
||||||
const std::vector<std::string_view> base_hex_test{"0", "1", "F",
|
std::vector<std::string_view> const base_hex_test{"0", "1", "F",
|
||||||
"01f", "0x11", "10X11"};
|
"01f", "0x11", "10X11"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < base_hex_test.size(); ++i) {
|
for (std::size_t i = 0; i < base_hex_test.size(); ++i) {
|
||||||
const auto &f = base_hex_test[i];
|
auto const &f = base_hex_test[i];
|
||||||
int result;
|
int result;
|
||||||
auto answer =
|
auto answer =
|
||||||
fast_float::from_chars(f.data(), f.data() + f.size(), result, 16);
|
fast_float::from_chars(f.data(), f.data() + f.size(), result, 16);
|
||||||
@ -459,11 +459,11 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// invalid base test #1 (-1)
|
// invalid base test #1 (-1)
|
||||||
const std::vector<std::string_view> invalid_base_test_1{"0", "1", "-1", "F",
|
std::vector<std::string_view> const invalid_base_test_1{"0", "1", "-1", "F",
|
||||||
"10Z"};
|
"10Z"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < invalid_base_test_1.size(); ++i) {
|
for (std::size_t i = 0; i < invalid_base_test_1.size(); ++i) {
|
||||||
const auto &f = invalid_base_test_1[i];
|
auto const &f = invalid_base_test_1[i];
|
||||||
int result;
|
int result;
|
||||||
auto answer =
|
auto answer =
|
||||||
fast_float::from_chars(f.data(), f.data() + f.size(), result, -1);
|
fast_float::from_chars(f.data(), f.data() + f.size(), result, -1);
|
||||||
@ -475,11 +475,11 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// invalid base test #2 (37)
|
// invalid base test #2 (37)
|
||||||
const std::vector<std::string_view> invalid_base_test_2{"0", "1", "F", "Z",
|
std::vector<std::string_view> const invalid_base_test_2{"0", "1", "F", "Z",
|
||||||
"10Z"};
|
"10Z"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < invalid_base_test_2.size(); ++i) {
|
for (std::size_t i = 0; i < invalid_base_test_2.size(); ++i) {
|
||||||
const auto &f = invalid_base_test_2[i];
|
auto const &f = invalid_base_test_2[i];
|
||||||
int result;
|
int result;
|
||||||
auto answer =
|
auto answer =
|
||||||
fast_float::from_chars(f.data(), f.data() + f.size(), result, 37);
|
fast_float::from_chars(f.data(), f.data() + f.size(), result, 37);
|
||||||
@ -491,7 +491,7 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// int out of range error base test (64 bit)
|
// int out of range error base test (64 bit)
|
||||||
const std::vector<std::string_view> int_out_of_range_base_test{
|
std::vector<std::string_view> const int_out_of_range_base_test{
|
||||||
"1000000000000000000000000000000000000000000000000000000000000000",
|
"1000000000000000000000000000000000000000000000000000000000000000",
|
||||||
"-1000000000000000000000000000000000000000000000000000000000000001",
|
"-1000000000000000000000000000000000000000000000000000000000000001",
|
||||||
"2021110011022210012102010021220101220222",
|
"2021110011022210012102010021220101220222",
|
||||||
@ -564,7 +564,7 @@ int main() {
|
|||||||
"-1Y2P0IJ32E8E9"};
|
"-1Y2P0IJ32E8E9"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < int_out_of_range_base_test.size(); ++i) {
|
for (std::size_t i = 0; i < int_out_of_range_base_test.size(); ++i) {
|
||||||
const auto &f = int_out_of_range_base_test[i];
|
auto const &f = int_out_of_range_base_test[i];
|
||||||
int64_t result;
|
int64_t result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result,
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result,
|
||||||
int(2 + (i / 2)));
|
int(2 + (i / 2)));
|
||||||
@ -576,7 +576,7 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// unsigned out of range error base test (64 bit)
|
// unsigned out of range error base test (64 bit)
|
||||||
const std::vector<std::string_view> unsigned_out_of_range_base_test{
|
std::vector<std::string_view> const unsigned_out_of_range_base_test{
|
||||||
"10000000000000000000000000000000000000000000000000000000000000000",
|
"10000000000000000000000000000000000000000000000000000000000000000",
|
||||||
"11112220022122120101211020120210210211221",
|
"11112220022122120101211020120210210211221",
|
||||||
"100000000000000000000000000000000",
|
"100000000000000000000000000000000",
|
||||||
@ -614,7 +614,7 @@ int main() {
|
|||||||
"3W5E11264SGSG"};
|
"3W5E11264SGSG"};
|
||||||
int base_unsigned = 2;
|
int base_unsigned = 2;
|
||||||
for (std::size_t i = 0; i < unsigned_out_of_range_base_test.size(); ++i) {
|
for (std::size_t i = 0; i < unsigned_out_of_range_base_test.size(); ++i) {
|
||||||
const auto &f = unsigned_out_of_range_base_test[i];
|
auto const &f = unsigned_out_of_range_base_test[i];
|
||||||
uint64_t result;
|
uint64_t result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result,
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result,
|
||||||
base_unsigned);
|
base_unsigned);
|
||||||
@ -627,7 +627,7 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// just within range base test (64 bit)
|
// just within range base test (64 bit)
|
||||||
const std::vector<std::string_view> int_within_range_base_test{
|
std::vector<std::string_view> const int_within_range_base_test{
|
||||||
"111111111111111111111111111111111111111111111111111111111111111",
|
"111111111111111111111111111111111111111111111111111111111111111",
|
||||||
"-1000000000000000000000000000000000000000000000000000000000000000",
|
"-1000000000000000000000000000000000000000000000000000000000000000",
|
||||||
"2021110011022210012102010021220101220221",
|
"2021110011022210012102010021220101220221",
|
||||||
@ -700,7 +700,7 @@ int main() {
|
|||||||
"-1Y2P0IJ32E8E8"};
|
"-1Y2P0IJ32E8E8"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < int_within_range_base_test.size(); ++i) {
|
for (std::size_t i = 0; i < int_within_range_base_test.size(); ++i) {
|
||||||
const auto &f = int_within_range_base_test[i];
|
auto const &f = int_within_range_base_test[i];
|
||||||
int64_t result;
|
int64_t result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result,
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result,
|
||||||
int(2 + (i / 2)));
|
int(2 + (i / 2)));
|
||||||
@ -712,7 +712,7 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// unsigned within range base test (64 bit)
|
// unsigned within range base test (64 bit)
|
||||||
const std::vector<std::string_view> unsigned_within_range_base_test{
|
std::vector<std::string_view> const unsigned_within_range_base_test{
|
||||||
"1111111111111111111111111111111111111111111111111111111111111111",
|
"1111111111111111111111111111111111111111111111111111111111111111",
|
||||||
"11112220022122120101211020120210210211220",
|
"11112220022122120101211020120210210211220",
|
||||||
"33333333333333333333333333333333",
|
"33333333333333333333333333333333",
|
||||||
@ -750,7 +750,7 @@ int main() {
|
|||||||
"3W5E11264SGSF"};
|
"3W5E11264SGSF"};
|
||||||
int base_unsigned2 = 2;
|
int base_unsigned2 = 2;
|
||||||
for (std::size_t i = 0; i < unsigned_within_range_base_test.size(); ++i) {
|
for (std::size_t i = 0; i < unsigned_within_range_base_test.size(); ++i) {
|
||||||
const auto &f = unsigned_within_range_base_test[i];
|
auto const &f = unsigned_within_range_base_test[i];
|
||||||
uint64_t result;
|
uint64_t result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result,
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result,
|
||||||
base_unsigned2);
|
base_unsigned2);
|
||||||
@ -764,7 +764,7 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// int leading zeros test
|
// int leading zeros test
|
||||||
const std::vector<std::string_view> int_leading_zeros_test{
|
std::vector<std::string_view> const int_leading_zeros_test{
|
||||||
"000000000000000000000000000000000000000000000000000000000000000000000011"
|
"000000000000000000000000000000000000000000000000000000000000000000000011"
|
||||||
"11110111",
|
"11110111",
|
||||||
"000000000000000000000000000000000000000000000000001101121",
|
"000000000000000000000000000000000000000000000000001101121",
|
||||||
@ -803,7 +803,7 @@ int main() {
|
|||||||
"00000000000000000000S7"};
|
"00000000000000000000S7"};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < int_leading_zeros_test.size(); ++i) {
|
for (std::size_t i = 0; i < int_leading_zeros_test.size(); ++i) {
|
||||||
const auto &f = int_leading_zeros_test[i];
|
auto const &f = int_leading_zeros_test[i];
|
||||||
int result;
|
int result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result,
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result,
|
||||||
int(i + 2));
|
int(i + 2));
|
||||||
|
|||||||
@ -13,13 +13,13 @@ int main() {
|
|||||||
// Write some testcases for the parsing of floating point numbers in the
|
// Write some testcases for the parsing of floating point numbers in the
|
||||||
// float32_t type. We use the from_chars function defined in this library.
|
// float32_t type. We use the from_chars function defined in this library.
|
||||||
#if __STDCPP_FLOAT32_T__
|
#if __STDCPP_FLOAT32_T__
|
||||||
const std::vector<std::float32_t> float32_test_expected{
|
std::vector<std::float32_t> const float32_test_expected{
|
||||||
123.456f, -78.9f, 0.0001f, 3.40282e+038f};
|
123.456f, -78.9f, 0.0001f, 3.40282e+038f};
|
||||||
const std::vector<std::string_view> float32_test{"123.456", "-78.9", "0.0001",
|
std::vector<std::string_view> const float32_test{"123.456", "-78.9", "0.0001",
|
||||||
"3.40282e+038"};
|
"3.40282e+038"};
|
||||||
std::cout << "runing float32 test" << std::endl;
|
std::cout << "runing float32 test" << std::endl;
|
||||||
for (std::size_t i = 0; i < float32_test.size(); ++i) {
|
for (std::size_t i = 0; i < float32_test.size(); ++i) {
|
||||||
const auto &f = float32_test[i];
|
auto const &f = float32_test[i];
|
||||||
std::float32_t result;
|
std::float32_t result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
||||||
|
|
||||||
@ -39,14 +39,14 @@ int main() {
|
|||||||
|
|
||||||
#if __STDCPP_FLOAT64_T__
|
#if __STDCPP_FLOAT64_T__
|
||||||
// Test cases for std::float64_t
|
// Test cases for std::float64_t
|
||||||
const std::vector<std::float64_t> float64_test_expected{
|
std::vector<std::float64_t> const float64_test_expected{
|
||||||
1.23e4, -5.67e-8, 1.7976931348623157e+308, -1.7976931348623157e+308};
|
1.23e4, -5.67e-8, 1.7976931348623157e+308, -1.7976931348623157e+308};
|
||||||
const std::vector<std::string_view> float64_test{"1.23e4", "-5.67e-8",
|
std::vector<std::string_view> const float64_test{"1.23e4", "-5.67e-8",
|
||||||
"1.7976931348623157e+308",
|
"1.7976931348623157e+308",
|
||||||
"-1.7976931348623157e+308"};
|
"-1.7976931348623157e+308"};
|
||||||
std::cout << "runing float64 test" << std::endl;
|
std::cout << "runing float64 test" << std::endl;
|
||||||
for (std::size_t i = 0; i < float64_test.size(); ++i) {
|
for (std::size_t i = 0; i < float64_test.size(); ++i) {
|
||||||
const auto &f = float64_test[i];
|
auto const &f = float64_test[i];
|
||||||
std::float64_t result;
|
std::float64_t result;
|
||||||
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
auto answer = fast_float::from_chars(f.data(), f.data() + f.size(), result);
|
||||||
|
|
||||||
|
|||||||
@ -7,7 +7,7 @@
|
|||||||
#include "fast_float/fast_float.h"
|
#include "fast_float/fast_float.h"
|
||||||
|
|
||||||
int main_readme() {
|
int main_readme() {
|
||||||
const std::string input = "1d+4";
|
std::string const input = "1d+4";
|
||||||
double result;
|
double result;
|
||||||
fast_float::parse_options options{
|
fast_float::parse_options options{
|
||||||
fast_float::chars_format::fortran |
|
fast_float::chars_format::fortran |
|
||||||
@ -23,15 +23,15 @@ int main_readme() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
int main() {
|
int main() {
|
||||||
const std::vector<double> expected{10000, 1000, 100, 10, 1,
|
std::vector<double> const expected{10000, 1000, 100, 10, 1,
|
||||||
.1, .01, .001, .0001};
|
.1, .01, .001, .0001};
|
||||||
const std::vector<std::string> fmt1{"1+4", "1+3", "1+2", "1+1", "1+0",
|
std::vector<std::string> const fmt1{"1+4", "1+3", "1+2", "1+1", "1+0",
|
||||||
"1-1", "1-2", "1-3", "1-4"};
|
"1-1", "1-2", "1-3", "1-4"};
|
||||||
const std::vector<std::string> fmt2{"1d+4", "1d+3", "1d+2", "1d+1", "1d+0",
|
std::vector<std::string> const fmt2{"1d+4", "1d+3", "1d+2", "1d+1", "1d+0",
|
||||||
"1d-1", "1d-2", "1d-3", "1d-4"};
|
"1d-1", "1d-2", "1d-3", "1d-4"};
|
||||||
const std::vector<std::string> fmt3{"+1+4", "+1+3", "+1+2", "+1+1", "+1+0",
|
std::vector<std::string> const fmt3{"+1+4", "+1+3", "+1+2", "+1+1", "+1+0",
|
||||||
"+1-1", "+1-2", "+1-3", "+1-4"};
|
"+1-1", "+1-2", "+1-3", "+1-4"};
|
||||||
const fast_float::parse_options options{
|
fast_float::parse_options const options{
|
||||||
fast_float::chars_format::fortran |
|
fast_float::chars_format::fortran |
|
||||||
fast_float::chars_format::allow_leading_plus};
|
fast_float::chars_format::allow_leading_plus};
|
||||||
|
|
||||||
|
|||||||
@ -17,7 +17,7 @@ file(WRITE main.cpp "
|
|||||||
#include <iostream>
|
#include <iostream>
|
||||||
|
|
||||||
int main() {
|
int main() {
|
||||||
const std::string input = \"3.1416 xyz \";
|
std::string input = \"3.1416 xyz \";
|
||||||
double result;
|
double result;
|
||||||
auto answer = fast_float::from_chars(input.data(), input.data()+input.size(), result);
|
auto answer = fast_float::from_chars(input.data(), input.data()+input.size(), result);
|
||||||
if (answer.ec != std::errc()) { std::cerr << \"parsing failure\\n\"; return EXIT_FAILURE; }
|
if (answer.ec != std::errc()) { std::cerr << \"parsing failure\\n\"; return EXIT_FAILURE; }
|
||||||
|
|||||||
@ -5,7 +5,7 @@
|
|||||||
#include "fast_float/fast_float.h"
|
#include "fast_float/fast_float.h"
|
||||||
|
|
||||||
int main_readme() {
|
int main_readme() {
|
||||||
const std::string input = "+.1"; // not valid
|
std::string const input = "+.1"; // not valid
|
||||||
double result;
|
double result;
|
||||||
fast_float::parse_options options{
|
fast_float::parse_options options{
|
||||||
fast_float::chars_format::json |
|
fast_float::chars_format::json |
|
||||||
@ -20,7 +20,7 @@ int main_readme() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
int main_readme2() {
|
int main_readme2() {
|
||||||
const std::string input = "inf"; // not valid in JSON
|
std::string const input = "inf"; // not valid in JSON
|
||||||
double result;
|
double result;
|
||||||
fast_float::parse_options options{
|
fast_float::parse_options options{
|
||||||
fast_float::chars_format::json |
|
fast_float::chars_format::json |
|
||||||
@ -35,7 +35,7 @@ int main_readme2() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
int main_readme3() {
|
int main_readme3() {
|
||||||
const std::string input =
|
std::string const input =
|
||||||
"inf"; // not valid in JSON but we allow it with json_or_infnan
|
"inf"; // not valid in JSON but we allow it with json_or_infnan
|
||||||
double result;
|
double result;
|
||||||
fast_float::parse_options options{
|
fast_float::parse_options options{
|
||||||
@ -69,7 +69,7 @@ struct RejectedValue {
|
|||||||
};
|
};
|
||||||
|
|
||||||
int main() {
|
int main() {
|
||||||
const std::vector<AcceptedValue> accept{
|
std::vector<AcceptedValue> const accept{
|
||||||
{"-0.2", {-0.2, ""}},
|
{"-0.2", {-0.2, ""}},
|
||||||
{"0.02", {0.02, ""}},
|
{"0.02", {0.02, ""}},
|
||||||
{"0.002", {0.002, ""}},
|
{"0.002", {0.002, ""}},
|
||||||
@ -78,7 +78,7 @@ int main() {
|
|||||||
{"1e", {1., "e"}},
|
{"1e", {1., "e"}},
|
||||||
{"1e+", {1., "e+"}},
|
{"1e+", {1., "e+"}},
|
||||||
{"inf", {std::numeric_limits<double>::infinity(), ""}}};
|
{"inf", {std::numeric_limits<double>::infinity(), ""}}};
|
||||||
const std::vector<RejectedValue> reject{
|
std::vector<RejectedValue> const reject{
|
||||||
{"-.2", {fast_float::parse_error::missing_integer_after_sign, 1}},
|
{"-.2", {fast_float::parse_error::missing_integer_after_sign, 1}},
|
||||||
{"00.02", {fast_float::parse_error::leading_zeros_in_integer_part, 0}},
|
{"00.02", {fast_float::parse_error::leading_zeros_in_integer_part, 0}},
|
||||||
{"0.e+1", {fast_float::parse_error::no_digits_in_fractional_part, 2}},
|
{"0.e+1", {fast_float::parse_error::no_digits_in_fractional_part, 2}},
|
||||||
@ -92,8 +92,8 @@ int main() {
|
|||||||
{"nan(snan)", {fast_float::parse_error::no_digits_in_integer_part, 0}}};
|
{"nan(snan)", {fast_float::parse_error::no_digits_in_integer_part, 0}}};
|
||||||
|
|
||||||
for (std::size_t i = 0; i < accept.size(); ++i) {
|
for (std::size_t i = 0; i < accept.size(); ++i) {
|
||||||
const auto &s = accept[i].input;
|
auto const &s = accept[i].input;
|
||||||
const auto &expected = accept[i].expected;
|
auto const &expected = accept[i].expected;
|
||||||
double result;
|
double result;
|
||||||
auto answer =
|
auto answer =
|
||||||
fast_float::from_chars(s.data(), s.data() + s.size(), result,
|
fast_float::from_chars(s.data(), s.data() + s.size(), result,
|
||||||
@ -116,7 +116,7 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
for (std::size_t i = 0; i < reject.size(); ++i) {
|
for (std::size_t i = 0; i < reject.size(); ++i) {
|
||||||
const auto &s = reject[i].input;
|
auto const &s = reject[i].input;
|
||||||
double result;
|
double result;
|
||||||
auto answer = fast_float::from_chars(s.data(), s.data() + s.size(), result,
|
auto answer = fast_float::from_chars(s.data(), s.data() + s.size(), result,
|
||||||
fast_float::chars_format::json);
|
fast_float::chars_format::json);
|
||||||
@ -127,8 +127,8 @@ int main() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
for (std::size_t i = 0; i < reject.size(); ++i) {
|
for (std::size_t i = 0; i < reject.size(); ++i) {
|
||||||
const auto &f = reject[i].input;
|
auto const &f = reject[i].input;
|
||||||
const auto &expected_reason = reject[i].reason;
|
auto const &expected_reason = reject[i].reason;
|
||||||
auto answer = fast_float::parse_number_string(
|
auto answer = fast_float::parse_number_string(
|
||||||
f.data(), f.data() + f.size(),
|
f.data(), f.data() + f.size(),
|
||||||
fast_float::parse_options(
|
fast_float::parse_options(
|
||||||
|
|||||||
@ -25,7 +25,7 @@ void allvalues() {
|
|||||||
memcpy(&v, &word, sizeof(v));
|
memcpy(&v, &word, sizeof(v));
|
||||||
|
|
||||||
{
|
{
|
||||||
const char *string_end = to_string(v, buffer);
|
char const *string_end = to_string(v, buffer);
|
||||||
float result_value;
|
float result_value;
|
||||||
auto result = fast_float::from_chars(buffer, string_end, result_value);
|
auto result = fast_float::from_chars(buffer, string_end, result_value);
|
||||||
// Starting with version 4.0 for fast_float, we return result_out_of_range
|
// Starting with version 4.0 for fast_float, we return result_out_of_range
|
||||||
|
|||||||
@ -24,7 +24,7 @@ void all_32bit_values() {
|
|||||||
double v = v32;
|
double v = v32;
|
||||||
|
|
||||||
{
|
{
|
||||||
const char *string_end = to_string(v, buffer);
|
char const *string_end = to_string(v, buffer);
|
||||||
double result_value;
|
double result_value;
|
||||||
auto result = fast_float::from_chars(buffer, string_end, result_value);
|
auto result = fast_float::from_chars(buffer, string_end, result_value);
|
||||||
// Starting with version 4.0 for fast_float, we return result_out_of_range
|
// Starting with version 4.0 for fast_float, we return result_out_of_range
|
||||||
|
|||||||
@ -53,7 +53,7 @@ void random_values(size_t N) {
|
|||||||
double v;
|
double v;
|
||||||
memcpy(&v, &word, sizeof(v));
|
memcpy(&v, &word, sizeof(v));
|
||||||
{
|
{
|
||||||
const char *string_end = to_string(v, buffer);
|
char const *string_end = to_string(v, buffer);
|
||||||
double result_value;
|
double result_value;
|
||||||
auto result = fast_float::from_chars(buffer, string_end, result_value);
|
auto result = fast_float::from_chars(buffer, string_end, result_value);
|
||||||
// Starting with version 4.0 for fast_float, we return result_out_of_range
|
// Starting with version 4.0 for fast_float, we return result_out_of_range
|
||||||
|
|||||||
@ -19,8 +19,8 @@ template <typename T> bool test() {
|
|||||||
"2.71828182845904523536028747135266249775724709369995";
|
"2.71828182845904523536028747135266249775724709369995";
|
||||||
std::vector<T> answers = {T(0.15625), T(3.141592653589793),
|
std::vector<T> answers = {T(0.15625), T(3.141592653589793),
|
||||||
T(2.718281828459045)};
|
T(2.718281828459045)};
|
||||||
const char *begin = input.data();
|
char const *begin = input.data();
|
||||||
const char *end = input.data() + input.size();
|
char const *end = input.data() + input.size();
|
||||||
for (size_t i = 0; i < answers.size(); i++) {
|
for (size_t i = 0; i < answers.size(); i++) {
|
||||||
T result_value;
|
T result_value;
|
||||||
while ((begin < end) && (std::isspace(*begin))) {
|
while ((begin < end) && (std::isspace(*begin))) {
|
||||||
|
|||||||
@ -16,7 +16,7 @@
|
|||||||
// gcc.
|
// gcc.
|
||||||
#include <locale>
|
#include <locale>
|
||||||
// workaround for CYGWIN
|
// workaround for CYGWIN
|
||||||
double cygwin_strtod_l(const char *start, char **end) {
|
double cygwin_strtod_l(char const *start, char **end) {
|
||||||
double d;
|
double d;
|
||||||
std::stringstream ss;
|
std::stringstream ss;
|
||||||
ss.imbue(std::locale::classic());
|
ss.imbue(std::locale::classic());
|
||||||
@ -32,7 +32,7 @@ double cygwin_strtod_l(const char *start, char **end) {
|
|||||||
*end = const_cast<char *>(start) + nread;
|
*end = const_cast<char *>(start) + nread;
|
||||||
return d;
|
return d;
|
||||||
}
|
}
|
||||||
float cygwin_strtof_l(const char *start, char **end) {
|
float cygwin_strtof_l(char const *start, char **end) {
|
||||||
float d;
|
float d;
|
||||||
std::stringstream ss;
|
std::stringstream ss;
|
||||||
ss.imbue(std::locale::classic());
|
ss.imbue(std::locale::classic());
|
||||||
@ -50,7 +50,7 @@ float cygwin_strtof_l(const char *start, char **end) {
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
std::pair<double, bool> strtod_from_string(const char *st) {
|
std::pair<double, bool> strtod_from_string(char const *st) {
|
||||||
double d;
|
double d;
|
||||||
char *pr;
|
char *pr;
|
||||||
#if defined(__CYGWIN__) || defined(__MINGW32__) || defined(__MINGW64__) || \
|
#if defined(__CYGWIN__) || defined(__MINGW32__) || defined(__MINGW64__) || \
|
||||||
|
|||||||
@ -56,7 +56,7 @@ void random_values(size_t N) {
|
|||||||
memcpy(&v, &word, sizeof(v));
|
memcpy(&v, &word, sizeof(v));
|
||||||
// if (!std::isnormal(v))
|
// if (!std::isnormal(v))
|
||||||
{
|
{
|
||||||
const char *string_end = to_string(v, buffer);
|
char const *string_end = to_string(v, buffer);
|
||||||
double result_value;
|
double result_value;
|
||||||
auto result = fast_float::from_chars(buffer, string_end, result_value);
|
auto result = fast_float::from_chars(buffer, string_end, result_value);
|
||||||
// Starting with version 4.0 for fast_float, we return result_out_of_range
|
// Starting with version 4.0 for fast_float, we return result_out_of_range
|
||||||
|
|||||||
@ -15,7 +15,7 @@
|
|||||||
#include <locale>
|
#include <locale>
|
||||||
#include <sstream>
|
#include <sstream>
|
||||||
// workaround for CYGWIN
|
// workaround for CYGWIN
|
||||||
double cygwin_strtod_l(const char *start, char **end) {
|
double cygwin_strtod_l(char const *start, char **end) {
|
||||||
double d;
|
double d;
|
||||||
std::stringstream ss;
|
std::stringstream ss;
|
||||||
ss.imbue(std::locale::classic());
|
ss.imbue(std::locale::classic());
|
||||||
@ -31,7 +31,7 @@ double cygwin_strtod_l(const char *start, char **end) {
|
|||||||
*end = const_cast<char *>(start) + nread;
|
*end = const_cast<char *>(start) + nread;
|
||||||
return d;
|
return d;
|
||||||
}
|
}
|
||||||
float cygwin_strtof_l(const char *start, char **end) {
|
float cygwin_strtof_l(char const *start, char **end) {
|
||||||
float d;
|
float d;
|
||||||
std::stringstream ss;
|
std::stringstream ss;
|
||||||
ss.imbue(std::locale::classic());
|
ss.imbue(std::locale::classic());
|
||||||
|
|||||||
@ -73,7 +73,7 @@ bool eddelbuettel() {
|
|||||||
bool non_space_trailing_content = false;
|
bool non_space_trailing_content = false;
|
||||||
if (answer.ptr != input.data() + input.size()) {
|
if (answer.ptr != input.data() + input.size()) {
|
||||||
// check that there is no content left
|
// check that there is no content left
|
||||||
for (const char *leftover = answer.ptr;
|
for (char const *leftover = answer.ptr;
|
||||||
leftover != input.data() + input.size(); leftover++) {
|
leftover != input.data() + input.size(); leftover++) {
|
||||||
if (!fast_float::is_space(*leftover)) {
|
if (!fast_float::is_space(*leftover)) {
|
||||||
non_space_trailing_content = true;
|
non_space_trailing_content = true;
|
||||||
|
|||||||
@ -15,7 +15,7 @@
|
|||||||
#include <locale>
|
#include <locale>
|
||||||
#include <sstream>
|
#include <sstream>
|
||||||
// workaround for CYGWIN
|
// workaround for CYGWIN
|
||||||
double cygwin_strtod_l(const char *start, char **end) {
|
double cygwin_strtod_l(char const *start, char **end) {
|
||||||
double d;
|
double d;
|
||||||
std::stringstream ss;
|
std::stringstream ss;
|
||||||
ss.imbue(std::locale::classic());
|
ss.imbue(std::locale::classic());
|
||||||
@ -31,7 +31,7 @@ double cygwin_strtod_l(const char *start, char **end) {
|
|||||||
*end = const_cast<char *>(start) + nread;
|
*end = const_cast<char *>(start) + nread;
|
||||||
return d;
|
return d;
|
||||||
}
|
}
|
||||||
float cygwin_strtof_l(const char *start, char **end) {
|
float cygwin_strtof_l(char const *start, char **end) {
|
||||||
float d;
|
float d;
|
||||||
std::stringstream ss;
|
std::stringstream ss;
|
||||||
ss.imbue(std::locale::classic());
|
ss.imbue(std::locale::classic());
|
||||||
|
|||||||
@ -17,7 +17,7 @@
|
|||||||
#include <locale>
|
#include <locale>
|
||||||
#include <sstream>
|
#include <sstream>
|
||||||
// workaround for CYGWIN
|
// workaround for CYGWIN
|
||||||
double cygwin_strtod_l(const char *start, char **end) {
|
double cygwin_strtod_l(char const *start, char **end) {
|
||||||
double d;
|
double d;
|
||||||
std::stringstream ss;
|
std::stringstream ss;
|
||||||
ss.imbue(std::locale::classic());
|
ss.imbue(std::locale::classic());
|
||||||
@ -33,7 +33,7 @@ double cygwin_strtod_l(const char *start, char **end) {
|
|||||||
*end = const_cast<char *>(start) + nread;
|
*end = const_cast<char *>(start) + nread;
|
||||||
return d;
|
return d;
|
||||||
}
|
}
|
||||||
float cygwin_strtof_l(const char *start, char **end) {
|
float cygwin_strtof_l(char const *start, char **end) {
|
||||||
float d;
|
float d;
|
||||||
std::stringstream ss;
|
std::stringstream ss;
|
||||||
ss.imbue(std::locale::classic());
|
ss.imbue(std::locale::classic());
|
||||||
@ -93,8 +93,8 @@ template <typename T> bool test() {
|
|||||||
std::errc(),
|
std::errc(),
|
||||||
std::errc(),
|
std::errc(),
|
||||||
std::errc()};
|
std::errc()};
|
||||||
const char *begin = input.data();
|
char const *begin = input.data();
|
||||||
const char *end = input.data() + input.size();
|
char const *end = input.data() + input.size();
|
||||||
for (size_t i = 0; i < answers.size(); i++) {
|
for (size_t i = 0; i < answers.size(); i++) {
|
||||||
T result_value;
|
T result_value;
|
||||||
while ((begin < end) && (std::isspace(*begin))) {
|
while ((begin < end) && (std::isspace(*begin))) {
|
||||||
@ -120,9 +120,9 @@ template <typename T> bool test() {
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
template <typename T> void strtod_from_string(const std::string &st, T &d);
|
template <typename T> void strtod_from_string(std::string const &st, T &d);
|
||||||
|
|
||||||
template <> void strtod_from_string(const std::string &st, double &d) {
|
template <> void strtod_from_string(std::string const &st, double &d) {
|
||||||
char *pr = (char *)st.c_str();
|
char *pr = (char *)st.c_str();
|
||||||
#if defined(__CYGWIN__) || defined(__MINGW32__) || defined(__MINGW64__) || \
|
#if defined(__CYGWIN__) || defined(__MINGW32__) || defined(__MINGW64__) || \
|
||||||
defined(sun) || defined(__sun)
|
defined(sun) || defined(__sun)
|
||||||
@ -139,7 +139,7 @@ template <> void strtod_from_string(const std::string &st, double &d) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
template <> void strtod_from_string(const std::string &st, float &d) {
|
template <> void strtod_from_string(std::string const &st, float &d) {
|
||||||
char *pr = (char *)st.c_str();
|
char *pr = (char *)st.c_str();
|
||||||
#if defined(__CYGWIN__) || defined(__MINGW32__) || defined(__MINGW64__) || \
|
#if defined(__CYGWIN__) || defined(__MINGW32__) || defined(__MINGW64__) || \
|
||||||
defined(sun) || defined(__sun)
|
defined(sun) || defined(__sun)
|
||||||
@ -160,7 +160,7 @@ template <typename T> bool partow_test() {
|
|||||||
// credit:
|
// credit:
|
||||||
// https://github.com/ArashPartow/strtk/blob/master/strtk_tokenizer_cmp.cpp#L568
|
// https://github.com/ArashPartow/strtk/blob/master/strtk_tokenizer_cmp.cpp#L568
|
||||||
// MIT license
|
// MIT license
|
||||||
const std::string strint_list[] = {
|
std::string const strint_list[] = {
|
||||||
"9007199254740993",
|
"9007199254740993",
|
||||||
"9007199254740994",
|
"9007199254740994",
|
||||||
"9007199254740995",
|
"9007199254740995",
|
||||||
@ -1085,7 +1085,7 @@ template <typename T> bool partow_test() {
|
|||||||
"1234567890",
|
"1234567890",
|
||||||
"-1234567890",
|
"-1234567890",
|
||||||
};
|
};
|
||||||
for (const std::string &st : strint_list) {
|
for (std::string const &st : strint_list) {
|
||||||
T expected_value;
|
T expected_value;
|
||||||
strtod_from_string(st, expected_value);
|
strtod_from_string(st, expected_value);
|
||||||
T result_value;
|
T result_value;
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user