FILE * 在正确读取之前的条目后,正在从输入文本文件中将零读入 'double' 变量

FILE * is reading zeros into a 'double' variable from input text file after reading previous entries correctly

手头的任务是从输入文件“as5input.txt”中读取值,并对这些值进行一些基本的线性计算,以便稍后将它们写入另一个输出文本文件。使用 'fscanf()' 它成功读取了前两行数据,然后在应该读取实际值时继续只读取零。

我在 fscanf 上尝试了不同的格式,并尝试直接读取以查看它正在读取的值。我确保输入文件中没有可能导致问题的 '\n' 或 ' ' 字符。我还尝试制作一个具有相同格式的新文本文件,以确保该文件没有任何奇怪的错误。但是,它仍然读取零。

我认为这与读取一个 int 然后读取一个 double 有关,但我不明白为什么会这样。

这是我正在使用的文本文件:

as5input.txt

2.0 5.0
6
1.0 2.0 4.0 8.0 16.0 31.0

这是与之交互的程序:

as5.c

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

struct instance_struct
{
    int count;
    float m, b;
    double * x, * y;
};

typedef struct instance_struct instance;

void instance_print(instance *is, FILE * ofp)
{
    int i;

    fprintf(ofp, "  y = %f x + %f\n", is->m, is->b);

    for (i = 0; i < is -> count; i++)
    {
        fprintf(ofp, "  x: %f   y: %f\n", is->x[i], is->y[i]);
    }
}

instance * make_instance(int count, float m, float b) {
    instance * is = (instance *)malloc(sizeof(instance));
    is -> m = m;
    is -> b = b;
    is -> count = count;
    is -> x = (double *)malloc(sizeof(double) * count);
    is -> y = (double *)malloc(sizeof(double) * count);
    return is;
}

int main(void)
{
    int i, count;
    float m, b;

    FILE *ifp, *ofp;
    ifp = fopen("as5input.txt", "r");
    ofp = fopen("out.txt", "w");

    fscanf(ifp, "%f %f %d", &m, &b, &count);

    double temp;
    instance * is = make_instance(count, m, b);
    for (i = 0; i < count; i++) {
        fscanf(ifp, "%f", &temp);
        printf("%f\n", temp);
        is -> x[i] = temp;
        is -> y[i] = m * temp + b;
    }

    instance_print(is, ofp);

    fclose(ifp);
    fclose(ofp);

    return 0;
}

这是输出文件中的结果:

out.txt

  y = 2.000000 x + 5.000000
  x: 0.000000   y: 5.000000
  x: 0.000000   y: 5.000000
  x: 0.000000   y: 5.000000
  x: 0.000000   y: 5.000000
  x: 0.000000   y: 5.000000
  x: 0.000000   y: 5.000000

这就是第 51 行 printf 的结果:

0.000000
0.000000
0.000000
0.000000
0.000000
0.000000

我可能遗漏了一些非常简单的东西,但奇怪的是它能正确读取斜率、截距和计数 (m, b, count)。任何帮助或建议将不胜感激。

double temp;
instance * is = make_instance(count, m, b);
for (i = 0; i < count; i++) {
    fscanf(ifp, "%f", &temp);
    ...
}

您正在使用 %f 作为格式说明符,但传递的是 double*,而不是 float*。增加编译器的警告,您可能会看到这样的警告(例如 -Wall 代表 gcc/clang):

<source>:50:27: warning: format specifies type 'float *' but the argument has type 'double *' [-Wformat]
        fscanf(ifp, "%f", &temp);
                     ~~   ^~~~~
                     %lf

解决方案是将 temp 设为 float 或使用 %lf 作为格式说明符。

请注意,printf%f 说明符用于 double,因为 floats 作为 doubles 传递给采用可变数量的函数争论。这不适用于指针。