什么阻碍了std :: to_chars和std :: from_chars的实现

时间:2019-09-06 16:09:09

标签: c++ c++17 floating-point-conversion

根据https://en.cppreference.com/w/cpp/compiler_support#cpp17,尚无主要供应商支持std::to_charsstd::from_chars的浮点版本。我知道正确格式化浮点数并不容易,但是C库中存在实现。但是,这些受到环境的影响,这是向标准中添加std::to_charsstd::from_chars的原因之一。如果您重构C库以依赖于将实际转换基础转换为某种中间格式的通用低级例程,那么这些功能的实现就不会是免费提供的。然后std::to_charsstd::from_chars可以或多或少地直接使用结果,以及C和C ++中更高级的API:(printfatof,{{1 }},strtodstd::stof)可以做更多更有趣的事情。

2 个答案:

答案 0 :(得分:4)

to/from_chars功能要求实现提供与自身的往返保证。具体来说,以下必须工作:

float f = //get some float
char chars[LOTS_OF_CHARS];
auto result = to_chars(chars, chars + sizeof(chars), f);
float g;
from_chars(chars, result.ptr, g);
assert(f == g);

该保证实际上很难实现,并且标准库C或C ++浮点到字符串到浮点函数都没有提供 ever 来提供保证。因此,您不仅可以从printf/scanfstof/to_string中获取代码,删除区域设置内容,然后将其称为to/from_chars实现。

答案 1 :(得分:-1)

这是一半答案,一半问题:

我找到了一个讨论主题,其中提到了需求

  

字符串表示形式由最小个   使得基数前至少有一位数字的字符   点(如果存在)并使用   相应的std :: from_chars函数可以准确地恢复值

但是C库不支持。但是,如果措词至少是 个字符 ,那么我猜

std::lock_guard l{local_mutex};
auto loc = setlocale(LC_ALL, nullptr);
setlocale(LC_ALL, "C");
char buffer[24]{};
sprintf(buffer, "%.17g", val);  // change to 9 for float
setlocale(LC_ALL, loc);

应该工作。我在这里正确吗?