root/software/fixed/parse_test.cc @ f12339cf
| 11ae9ac5 | David Sorber | #include <charconv>
|
||
#include <chrono>
|
||||
#include <cstdint>
|
||||
#include <cstdlib>
|
||||
#include <random>
|
||||
#include <iostream>
|
||||
#include <sstream>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include "fixed.h"
|
||||
// g++ -std=c++17 -O3 parse.cc -o parse
|
||||
void genRandomNumStrings(
|
||||
uint32_t number,
|
||||
std::vector<std::string>& values,
|
||||
uint64_t seed)
|
||||
{
|
||||
values.clear();
|
||||
std::random_device dev;
|
||||
//~ std::mt19937 rng(dev());
|
||||
std::mt19937 rng;
|
||||
rng.seed(seed);
|
||||
| 7fa2f28e | David Sorber | std::uniform_int_distribution<std::mt19937::result_type> numDigits(1, 18);
|
||
| 11ae9ac5 | David Sorber | std::uniform_int_distribution<std::mt19937::result_type> digits(0, 9);
|
||
for (uint32_t idx = 0; idx < number; ++idx)
|
||||
{
|
||||
std::ostringstream output;
|
||||
// Generate random whole number digits
|
||||
for (uint32_t wholeIdx = 0; wholeIdx < numDigits(rng); ++wholeIdx)
|
||||
{
|
||||
output << digits(rng);
|
||||
}
|
||||
output << ".";
|
||||
// Generate random fractional number digits
|
||||
for (uint32_t fracIdx = 0; fracIdx < numDigits(rng); ++fracIdx)
|
||||
{
|
||||
output << digits(rng);
|
||||
}
|
||||
values.emplace_back(output.str());
|
||||
//~ std::cout << "VAL: " << values.back() << std::endl;
|
||||
}
|
||||
}
|
||||
int main(int argc, char** argv)
|
||||
{
|
||||
std::cout << "Long Double Parse Test Util\n" << std::endl;
|
||||
if (argc < 3)
|
||||
{
|
||||
std::cerr << "ERROR: not enough arguments" << std::endl;
|
||||
return -1;
|
||||
}
|
||||
uint32_t parseType = std::strtoul(argv[1], nullptr, 10);
|
||||
uint32_t numRandomStrings = std::strtoul(argv[2], nullptr, 10);
|
||||
uint64_t seed = 0xDEADBEEF;
|
||||
if (argc > 3)
|
||||
{
|
||||
seed = std::strtoull(argv[3], nullptr, 0);
|
||||
}
|
||||
std::vector<std::string> values;
|
||||
{
|
||||
auto start = std::chrono::system_clock::now();
|
||||
genRandomNumStrings(numRandomStrings, values, seed);
|
||||
auto end = std::chrono::system_clock::now();
|
||||
auto diff = end - start;
|
||||
std::cout << "Time to generate " << numRandomStrings << " values: "
|
||||
<< std::chrono::duration <double, std::milli>(diff).count()
|
||||
<< " ms" << std::endl;
|
||||
}
|
||||
long double value = 0.0;
|
||||
fixed_64_64 fvalue;
|
||||
| 92782e4a | David Sorber | //~ fixed_128_128 f128value;
|
||
| 11ae9ac5 | David Sorber | |||
// 0) strtold()
|
||||
if (parseType == 0)
|
||||
{
|
||||
std::cout << "Parse type 0: std::strtold()" << std::endl;
|
||||
auto start = std::chrono::system_clock::now();
|
||||
for (auto& strValue : values)
|
||||
{
|
||||
value = std::strtold(strValue.c_str(), nullptr);
|
||||
//~ std::cout << "In: " << strValue << " -- Out: " << value << std::endl;
|
||||
}
|
||||
auto end = std::chrono::system_clock::now();
|
||||
auto diff = end - start;
|
||||
std::cout << "Total parse time: "
|
||||
<< std::chrono::duration <double, std::milli>(diff).count()
|
||||
<< " ms" << std::endl;
|
||||
}
|
||||
// 1) stold()
|
||||
else if (parseType == 1)
|
||||
{
|
||||
std::cout << "Parse type 1: std::stold()" << std::endl;
|
||||
auto start = std::chrono::system_clock::now();
|
||||
for (auto& strValue : values)
|
||||
{
|
||||
value = std::stold(strValue.c_str(), nullptr);
|
||||
//~ std::cout << "In: " << strValue << " -- Out: " << value << std::endl;
|
||||
}
|
||||
auto end = std::chrono::system_clock::now();
|
||||
auto diff = end - start;
|
||||
std::cout << "Total parse time: "
|
||||
<< std::chrono::duration <double, std::milli>(diff).count()
|
||||
<< " ms" << std::endl;
|
||||
}
|
||||
// 2) istringstream
|
||||
else if (parseType == 2)
|
||||
{
|
||||
std::cout << "Parse type 2: std::istringstream" << std::endl;
|
||||
auto start = std::chrono::system_clock::now();
|
||||
std::istringstream stream;
|
||||
for (auto& strValue : values)
|
||||
{
|
||||
stream.clear();
|
||||
stream.str(strValue);
|
||||
stream >> value;
|
||||
//~ std::cout << "In: " << strValue << " -- Out: " << value << std::endl;
|
||||
}
|
||||
auto end = std::chrono::system_clock::now();
|
||||
auto diff = end - start;
|
||||
std::cout << "Total parse time: "
|
||||
<< std::chrono::duration <double, std::milli>(diff).count()
|
||||
<< " ms" << std::endl;
|
||||
}
|
||||
// 3)
|
||||
else if (parseType == 3)
|
||||
{
|
||||
std::cout << "Parse type 3: fixed_64_64" << std::endl;
|
||||
auto start = std::chrono::system_clock::now();
|
||||
for (auto& strValue : values)
|
||||
{
|
||||
fvalue.parse(strValue.c_str());
|
||||
//~ std::cout << "In: " << strValue << " -- Out: " << fvalue << std::endl;
|
||||
}
|
||||
auto end = std::chrono::system_clock::now();
|
||||
auto diff = end - start;
|
||||
std::cout << "Total parse time: "
|
||||
<< std::chrono::duration <double, std::milli>(diff).count()
|
||||
<< " ms" << std::endl;
|
||||
}
|
||||
#if 0 // This needs >= gcc 11
|
||||
// 4) from_chars()
|
||||
else if (parseType == 4)
|
||||
{
|
||||
std::cout << "Parse type 4: std::from_chars()" << std::endl;
|
||||
auto start = std::chrono::system_clock::now();
|
||||
for (auto& strValue : values)
|
||||
{
|
||||
std::from_chars(strValue.begin(), strValue.end(),
|
||||
value, std::chars_format::general);
|
||||
//~ std::cout << "In: " << strValue << " -- Out: " << value << std::endl;
|
||||
}
|
||||
auto end = std::chrono::system_clock::now();
|
||||
auto diff = end - start;
|
||||
std::cout << "Total parse time: "
|
||||
<< std::chrono::duration <double, std::milli>(diff).count()
|
||||
<< " ms" << std::endl;
|
||||
}
|
||||
#endif
|
||||
| 92782e4a | David Sorber | #if 0
|
||
| 852d0468 | David Sorber | // 5)
|
||
else if (parseType == 5)
|
||||
{
|
||||
std::cout << "Parse type 5: fixed_128_128" << std::endl;
|
||||
auto start = std::chrono::system_clock::now();
|
||||
for (auto& strValue : values)
|
||||
{
|
||||
| 92782e4a | David Sorber | f128value.parse(strValue.c_str());
|
||
std::cout << "In: " << strValue << " -- Out: " << f128value << std::endl;
|
||||
| 852d0468 | David Sorber | }
|
||
auto end = std::chrono::system_clock::now();
|
||||
auto diff = end - start;
|
||||
std::cout << "Total parse time: "
|
||||
<< std::chrono::duration <double, std::milli>(diff).count()
|
||||
<< " ms" << std::endl;
|
||||
}
|
||||
| 92782e4a | David Sorber | #endif
|
||
| 11ae9ac5 | David Sorber | else
|
||
{
|
||||
std::cerr << "ERROR: invalid parse type: " << parseType << std::endl;
|
||||
return -2;
|
||||
}
|
||||
return 0;
|
||||
}
|