将字符串从 .csv 文件转换为双打
Converting Strings from a .csv file to doubles
在将字符串转换为双精度数时遇到问题。我试过使用 strtod
,但效果相同。看起来这应该只是 find 但可能使用 strtok
与它有关。 data[i].calories
当然是双倍的。
data[i].calories = atof(strtok(NULL, ","));
它似乎为卡路里分配了一个非常大的正数或负数(双精度,这意味着它一定是读错了值。
预期数据:
12cx7,23:55:00,->0.968900025,(this could also be a double),0,74,0,2,
它实际得到的是:
12cx7,23:55:00,->-537691972,0,0,74,0,2,
编辑:
我是个白痴,我把它显示为一个 INT PFFFFFFFFFFFFFFFF。
假设我们有这样的输入,
12cx7,23:55:00,0.968900025,,0,74,0,2,
我们愿意,
"Having trouble with the converting of strings to doubles."
那是我们要分隔字母数字数据。然后剩下的整数和浮点数,我们想以正确的格式打印,我会做如下的事情:
#include <cstring>
#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>
int isNumeric (const char * s)
{
if (s == NULL || *s == '[=10=]' || isspace(*s)) {
return 0;
}
char * p;
strtod (s, &p);
return *p == '[=10=]';
}
bool isInteger(double val)
{
int truncated = (int)val;
return (val == truncated);
}
int main() {
// If this is your input:
char input[100] = "12cx7,23:55:00,0.968900025,0,74,0,2,";
// Then step 1 -> we split the values
char *token = std::strtok(input, ",");
while (token != NULL) {
// Step 2 -> we check if the values in the string are numeric or otherwise
if (isNumeric(token)) {
// printf("%s\n", token);
char* endptr;
double v = strtod(token, &endptr);
// Step 3 -> we convert the strings containing no fractional parts to ints
if (isInteger(v)) {
int i = strtol(token, &endptr, 10);
printf("%d\n", i);
} else {
// Step 4 -> we print the remaining numeric-strings as floats
printf("%f\n", v);
}
}
else {
// What is not numeric, print as it is, like a string
printf("%s,",token);
}
token = std::strtok(NULL, ",");
}
}
对于 isInteger()
函数,我从 this 接受的答案中提取了 idea/code。其余部分非常原创,可能是 refined/improved.
这会产生这个输出:
12cx7,23:55:00,0.968900,0,74,0,2,
这基本上是我们想要的输出,除了非常重要的区别,即输入是一个完整的字符串而输出是 doubles/floats,整数和字符串被正确识别并以正确的格式打印。
编辑:
我这里不做任何错误处理。这段代码只是为了给 OP 一个概念验证。检查并控制使用的 strtoX
函数返回的任何错误。
在将字符串转换为双精度数时遇到问题。我试过使用 strtod
,但效果相同。看起来这应该只是 find 但可能使用 strtok
与它有关。 data[i].calories
当然是双倍的。
data[i].calories = atof(strtok(NULL, ","));
它似乎为卡路里分配了一个非常大的正数或负数(双精度,这意味着它一定是读错了值。
预期数据:
12cx7,23:55:00,->0.968900025,(this could also be a double),0,74,0,2,
它实际得到的是:
12cx7,23:55:00,->-537691972,0,0,74,0,2,
编辑:
我是个白痴,我把它显示为一个 INT PFFFFFFFFFFFFFFFF。
假设我们有这样的输入,
12cx7,23:55:00,0.968900025,,0,74,0,2,
我们愿意,
"Having trouble with the converting of strings to doubles."
那是我们要分隔字母数字数据。然后剩下的整数和浮点数,我们想以正确的格式打印,我会做如下的事情:
#include <cstring>
#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>
int isNumeric (const char * s)
{
if (s == NULL || *s == '[=10=]' || isspace(*s)) {
return 0;
}
char * p;
strtod (s, &p);
return *p == '[=10=]';
}
bool isInteger(double val)
{
int truncated = (int)val;
return (val == truncated);
}
int main() {
// If this is your input:
char input[100] = "12cx7,23:55:00,0.968900025,0,74,0,2,";
// Then step 1 -> we split the values
char *token = std::strtok(input, ",");
while (token != NULL) {
// Step 2 -> we check if the values in the string are numeric or otherwise
if (isNumeric(token)) {
// printf("%s\n", token);
char* endptr;
double v = strtod(token, &endptr);
// Step 3 -> we convert the strings containing no fractional parts to ints
if (isInteger(v)) {
int i = strtol(token, &endptr, 10);
printf("%d\n", i);
} else {
// Step 4 -> we print the remaining numeric-strings as floats
printf("%f\n", v);
}
}
else {
// What is not numeric, print as it is, like a string
printf("%s,",token);
}
token = std::strtok(NULL, ",");
}
}
对于 isInteger()
函数,我从 this 接受的答案中提取了 idea/code。其余部分非常原创,可能是 refined/improved.
这会产生这个输出:
12cx7,23:55:00,0.968900,0,74,0,2,
这基本上是我们想要的输出,除了非常重要的区别,即输入是一个完整的字符串而输出是 doubles/floats,整数和字符串被正确识别并以正确的格式打印。
编辑:
我这里不做任何错误处理。这段代码只是为了给 OP 一个概念验证。检查并控制使用的 strtoX
函数返回的任何错误。