无法使用fscanf读取C中的坐标

时间:2015-05-22 18:48:44

标签: c segmentation-fault coordinates scanf

我知道有人问过类似的问题,但似乎没有一个能解决我的问题。我运行代码时得到Segmentation fault (core dumped)

" data.dat"中的第一行具有文件中的总点数,下一行具有点坐标(以2维为单位)。我使用fgets阅读第一行,之后我使用fscanf阅读下一行。

这是我的代码:

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

int main(int argc, char *argv[]) {
    int n = atoi(argv[1]);
    FILE *fp;
    fp = fopen("data.dat","r");
    if (fp == NULL) {
        perror("Error");
    }

    int number;
    char str[3];

    fgets(str, 3, fp);
    number = atoi(str); // number of points to read from the file
    printf("number of lines: %d\n", number);

    // defining matrix to hold points
    float *P = (float *) malloc(sizeof(float)*2*number);

    int i = 0;
    while(i < number){
        int ret = fscanf(fp, "%f%f", P[i*number + 1], P[i*number + 2]);
        printf("%f  %f", P[i*number + 1], P[i*number + 2]);
        if (ret == 2){
            i++;
        }
    }
    fclose(fp);
    return 0;
}

编译这个没有给我任何错误,但确实给了我以下警告:

polynom.c: In function ‘main’:
polynom.c:32:24: warning: format ‘%f’ expects argument of type ‘float*’,but argument 3 has type ‘double’ [-Wformat=]

int ret = fscanf(fp, "%f%f", P[i*number + 1], P[i*number + 2]);
                    ^
polynom.c:32:24: warning: format ‘%f’ expects argument of type ‘float *’, but argument 4 has type ‘double’ [-Wformat=]

我之所以没有,因为我确实将参数3定义为float。

我使用命令行变量运行代码,因此Segmentation fault不是因为它。

4 个答案:

答案 0 :(得分:3)

应该是

while (2 == fscanf(fp, "%f%f", &P[i], &P[i+1]) {
    i += 2;
    if (i >= number*2)
        break;
}

答案 1 :(得分:2)

@Weather Vane很好地回答了主要问题。

以下是其他要点。

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

int main(int argc, char *argv[]) {
    // Check argc 
    if (argc < 1) Print_Error_And Quit();
    int n = atoi(argv[1]);
    FILE *fp;
    fp = fopen("data.dat","r");
    if (fp == NULL) {
        perror("Error");
    }

    int number;
    char str[3];

    // avoid naked magic numbers
    // fgets(str, 3, fp);
    fgets(str, sizeof str, fp);
    number = atoi(str); // number of points to read from the file
    printf("number of lines: %d\n", number);

    // defining matrix to hold points
    // No need for cast, avoid mis-match type/variable
    // float *P = (float *) malloc(sizeof(float)*2*number);
    float *P = malloc(2*number * sizeof *P);

    int i = 0;
    while(i < number){
        // int ret = fscanf(fp, "%f%f", P[i*number + 1], P[i*number + 2]);
        // reform
        int ret = fscanf(fp, "%f%f", &P[2*i], &P[2*i + 1]);
        // printf("%f  %f", P[i*number + 1], P[i*number + 2]);
        printf("%f  %f ", P[2*i], P[2*i + 1]);
        if (ret == 2){
            i++;
        }
        else {
          Likely_Should_Exit_Loop();
        }
    }
    fclose(fp);
    return 0;
}

答案 2 :(得分:0)

如果变量是"%lf",则需要使用double说明符,并且必须将变量的地址传递给scanf()而不是变量本身,例如

double value;

if (scanf("%lf", &value) == 1) 
{   /*        ^   ^ */
    /*        |   the address of operator. */
    /*       the correct speficier for `double' */
    fprintf(stdout, "%lf\n", value);
}

答案 3 :(得分:0)

malloc行返回一个指向一个区域的指针,该区域足够大以容纳数字* 2&#39;彩车。关于正确的声音,但实际上不会正常工作,因为一个浮动和下一个浮动之间没有区别。

推荐

struct twoFloat
{
    float float1;
    float float2;
};

然后

struct twoFloat* P = malloc(sizeof(struct twoFloat)*number);
if ( NULL == P ) { // handle error and exit }

// implied else, malloc successful
....

然后

    int ret = fscanf(fp, "%f%f", &P[i].float1, &P[i].float2);
    if (ret != 2) { // handle error and exit }

    // implied else, fscanf successful

    printf("%f  %f", P[i].float1, P[i].float2);
    i++;