Как читать и добавлять номера из текстового файла в C - PullRequest
1 голос
/ 23 апреля 2020

Я пытаюсь создать программу, которая читает числа из текстового файла с именем numbers.txt , который содержит разные числа в каждой строке.

Например:

8321
12
423
0
...

Я создал эту программу, но она не работает должным образом. Я перепробовал много вещей и не знаю, что делать. Кто-нибудь может направить меня в правильном направлении? Спасибо!

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

#define MAX_LEN 1000

int main(int argc, char *argv[]) {
    char str[MAX_LEN];
    FILE *pFile = fopen(argv[1], "r");
    int num;
    int sum = 0;
    int count = 0;

    if (pFile == NULL) {
        printf("Error opening file.\n");
        return 1;
    }

    while (!feof(pFile) && !ferror(pFile)) {
        if (fscanf(pFile, "%d", &num) == 1) {
            count++;
            while (strcmp(fgets(str, MAX_LEN, pFile), "\0") == 0) {
                printf("%s", str);
                //sum = sum + (int)(fgets(str, MAX_LEN, pFile));
                printf("\n");
            }
        }
    }
    fclose(pFile);

    printf("count = %d \n", count);
    printf("sum = %d \n", sum);

    return 0;
}

Ответы [ 3 ]

1 голос
/ 23 апреля 2020

strcmp(fgets(str, MAX_LEN, pFile),"\0") неправильно во многих отношениях. Например, аргумент strcmp должен быть строкой (нулевой указатель которой не является), но fgets возвращает NULL в случае ошибки или конца файла. Вам нужно убедиться, что он не вернул NULL, а затем вы можете сравнить строку в str. Однако нет необходимости strcmp против "\0" (или, в данном случае эквивалентно, ""), чтобы определить конец файла, потому что именно тогда fgets возвращает NULL.

Другая проблема заключается в том, что вы читаете как с fscanf, так и с fgets - выберите один и придерживайтесь его. Я рекомендую fgets, поскольку, как правило, легче получить правильную информацию (например, при неверном вводе намного сложнее восстановиться после fscanf и убедиться, что вы не застряли в бесконечном l oop, но при этом не потеряете ввод ). Конечно, вам нужно проанализировать целое число из str после fgets, но для этого есть много стандартных функций (например, strtol, atoi, sscanf).

Дон не используйте !feof(file) в качестве условия l oop (см., например, Почему «while (! feof (file))» всегда неверно? ). Если вы читаете с fgets, завершите l oop, когда он вернет NULL.

0 голосов
/ 23 апреля 2020

В вашей программе несколько проблем:

  • нет теста, если передан аргумент командной строки.
  • while (!feof(pFile) && !ferror(pFile)) всегда неверно перебирать файл: feof() дает действительная информация только после фактической попытки чтения. Просто проверьте, не удалось ли прочитать.
  • , если fscanf(pFile, "%d", &num) == 1) добавить число вместо простого подсчета чисел.
  • strcmp(fgets(str, MAX_LEN, pFile), "\0") завершится неудачно в конце файла, когда fgets() вернется NULL.

Если файл содержит только цифры, просто прочитайте эти цифры с помощью fscanf() и добавьте их по мере прохождения файла.

Вот измененная версия:

#include <stdio.h>

int main(int argc, char *argv[]) {
    FILE *pFile;
    int num
    int sum = 0;
    int count = 0;

    if (argc < 2) {
        printf("Missing filename\n");
        return 1;
    }
    if ((pFile = fopen(argv[1], "r")) == NULL) {
        printf("Error opening file %s\n", argv[1]);
        return 1;
    }
    while (fscanf(pFile, "%d", &num) == 1) {
        sum += num;
        count++;
    }
    fclose(pFile);

    printf("count = %d \n", count);
    printf("sum = %d \n", sum);

    return 0;
}
0 голосов
/ 23 апреля 2020

Вы можете использовать strtok, чтобы разделить числа в каждой строке, а затем использовать функцию atoi для преобразования строки в int.

Например:

while(fgets(str, MAX_LEN, pFile)) { 
   // if the numbers are separated by space character
   char *token = strtok(str, " ");
   while(token != NULL) {
       sum += atoi(token);
       strtok(NULL, " ");
   }
}

, если в строке только один номер, вам не нужно использовать strtok:

while(fgets(str, MAX_LEN, pFile)) { 
    sum += atoi(str);
    // OR
    sscanf(str,"%d\n", &new_number)
    sum += new_number;

}
...