Перевел parse_double на from_chars

This commit is contained in:
boolean-false 2026-09-20 18:55:59 +07:00
parent db53076c62
commit 7f408c11de
2 changed files with 32 additions and 17 deletions

View file

@ -1,6 +1,8 @@
#include "stringutil.hpp"
#include <algorithm>
#include <charconv>
#include <cctype>
#include <cmath>
#include <iomanip>
#include <locale>
@ -509,13 +511,18 @@ int util::replaceAll(
return replace_all(str, from, to);
}
// replace it with std::from_chars in the far far future
double util::parse_double(const std::string& str) {
std::istringstream ss(str);
ss.imbue(std::locale("C"));
double d;
ss >> d;
if (ss.fail()) {
const char* begin = str.data();
const char* end = begin + str.size();
while (begin != end && std::isspace(static_cast<unsigned char>(*begin))) {
begin++;
}
if (begin != end && *begin == '+') {
begin++;
}
double d = 0.0;
const auto result = std::from_chars(begin, end, d);
if (result.ec != std::errc()) {
throw std::runtime_error("invalid number format");
}
return d;

View file

@ -68,6 +68,14 @@ TEST(stringutil, base64_urlsafe) {
}
}
TEST(stringutil, parse_double) {
EXPECT_DOUBLE_EQ(util::parse_double("53.125"), 53.125);
EXPECT_DOUBLE_EQ(util::parse_double("-0.25"), -0.25);
EXPECT_DOUBLE_EQ(util::parse_double(" +12.5"), 12.5);
EXPECT_DOUBLE_EQ(util::parse_double("xx1.75yy", 2, 4), 1.75);
EXPECT_THROW(util::parse_double("not-a-number"), std::runtime_error);
}
class StringParser : BasicParser<char> {
public:
StringParser(std::string_view source) : BasicParser("<string>", source) {}