如何检查字符串是否可以转换为双精度C++
How to check if a string can be converted to double in C++?
我有一个字符串,它可以是一个数字(甚至是浮点数或双精度类型,而不仅仅是整数),它也可以是非数字的单词。
我想检查这个字符串是否可以转换为双精度,如果是这样,那么我想进行转换。如果是非数字字符串,我想要不同的行为。
我试过这个:
double tmp;
string str;
stringstream ss;
ss << str;
ss >> tmp;
if (ss.fail())
{
// non-numeric string
}
else
{
// string to double conversion is successful
}
这段代码的问题在于ss.fail()
总是true
的,即使tmp
包含正确的值。
有一个名为 atof()
的函数将字符串转换为双精度,但这不适合我,因为如果输入字符串是非数字0.0
它会返回值。这样我就无法区分非数字和零输入值。
如果你的输入字符串的类型来自 std::string,你可以使用这个函数(它适用于 Windows 和 unix 系统):
#include <stdlib.h>
#include <string>
/**
* @brief checkIsDouble - check inputString is double and if true return double result
* @param inputString - string for checking
* @param result - return double value
* @return true if string is double, false if not
*/
bool checkIsDouble(string inputString, double &result) {
char* end;
result = strtod(inputString.c_str(), &end);
if (end == inputString.c_str() || *end != ' ') return false;
return true;
}
std::stod呢?当它无法执行转换时,它将抛出 std::out_of_range。
try
{
double value = std::stod(input_string);
std::cout << "Converted string to a value of " << value << std::endl;
}
catch (const std::invalid_argument&)
{
std::cerr << "No conversion could be performed" << std::endl;
}
catch (const std::out_of_range&)
{
std::cerr << "Could not convert string to double, value falls out of range" << std::endl;
}
我还没有尝试编译它,但你应该明白这个想法。
也检查空格和流的结尾
if ((ss >> tmp) && (ss >> std::ws).eof() )
{
// a double
}
提取一个double
值,然后提取任何空格,如果在此期间遇到 eof,则表示您只有有效的double
小心使用 std::ws,因为它会触发 failbit,如果它已经是 EOF。因此,以下建议不适用于"9.000"之类的情况。由于 cl 错误,这在 Visual Studio 2015 中有效。但是在VS2019中,该错误已修复并失败。
if ((ss >> tmp) && (ss >> std::ws).eof() )
{
// a double
}
您可以考虑以下代码
if ((ss >> tmp) && ( ss.eof() || (ss >> std::ws).eof()) )
{
// a double
}
有关VS错误的详细信息:https://developercommunity.visualstudio.com/t/regression-stdws-incorrectly-sets-failbit-when-the/382896
一个不太像 cpp 的解决方案呢:
double number;
string str;
if (sscanf(str.c_str(), "%lf", &number) != 1)
{
// non-numeric string
}
else
{
// string to double conversion is successful
}
什么是有效数字?atof() 会解析什么,还是你对空格有规则?你允许科学记数法,前导-,前导+吗?其他数据可以跟随这个数字吗?必须有小数点还是接受整数?您接受裸前导小数点还是必须以 0 开头?你接受 00.1 吗?你接受 0.1FRED 但拒绝 0.1.2FRED 吗?
atof() 函数 strtod() 现在是针对此问题而设计的,因为它不够健壮,无法处理格式错误的输入。然而,strtod() 不够灵活,无法接受格式正确的输入的特定规则。如果规则很简单,那么编写自己的临时匹配器并不难 - 跳过whitepspace,匹配数字,匹配小数点,匹配数字,跳过空格。如果你需要完全的灵活性,最终你必须求助于正则表达式,这是一种大锤式的答案。
- 防止主数据类型C++的隐式转换
- 模板参数替换失败,并且未完成隐式转换
- 努力将整数转换为链表。不知道我在这里做错了什么
- HEX值到wchar_t字符(UTF-8)的转换
- lambda参数转换为constexpr技巧,然后获取带链接的数组
- 将 Qvector<uint8_t> 转换为 QString
- 如何在cuSparse中使用cusparseXcoo2csr从coo转换为csc
- 有关插入适配器的错误。[错误]请求从 'back_insert_iterator<vector<>>' 类型转换为非标量类型
- 在c++中使用nlohmann从类到json的转换
- 从"int*"强制转换为"unsigned int"会丢失精度错误
- 将Integer转换为4字节的unsined字符矢量(按大端字节顺序)
- 处理小于cpu数据总线的数据类型.(c++转换为机器代码)
- 如何使用OpenCV将RBG图像转换为HSV,并将H、S和V值保存为C++中的3个独立图像
- 复制列表初始化的隐式转换的等级是多少
- 正在将指针转换为范围
- 如何防止 c++ 在从浮点型转换为双精度型(不适用于 IO)时添加额外的小数?
- 将"打开的CV图像"中的"颜色"转换为整数格式
- 是否可以从int转换为enum类类型
- 了解 GLM- openGL 中的相机转换
- 将无符号char*转换为std::istream*C++