Использование fgets для пропуска пустой строки в C

#c

#c

Вопрос:

Моя программа используется для отображения чисел из a .Файл DAT. В каждой строке есть 2 поля. Например: содержимое файла .dat:

 1 2.2
3 10.9

10 100
  

В .Файл DAT. В первой строке поле 1 равно «1», а поле 2 равно «2.2» и так далее. Строка 3 — это пустая строка.

Моя программа используется для отображения чисел в том же формате, что и в .Файл DAT, который:

 1 2.2
3 10.9

10 100
  

Я делаю все свои программы в Ubuntu. Компиляция и запуск программы в gcc.

Мой код показан ниже:

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

int main()
{
    FILE *fp = fopen("number.dat", "r");
    if (fp == NULL)
    {
        fprintf(stderr, "ERROR: cannot open the filen");
        return 1;
    }

    char *field1 = NULL;
    char *field2 = NULL;

    char line[100];
    while(fgets(line, 100, fp)!=NULL)
    {
        if(line[0] != 'n')
        {
            field1 = strtok(line, " ");
            field2 = strtok(NULL, " ");

            printf("%s ", field1);
            printf("%s", field2);
        }
        else
        {
            printf("Blank Line!");
        }
     }
     fclose(fp);

     return 0;
}
  

Однако после запуска программы результат показан ниже:

 1 2.2
3 10.9

 (null)10 100
  

Я не понимаю, почему вместо «Пустой строки» отображается «(null)»!». Может кто-нибудь помочь мне выяснить, в чем проблема?

Комментарии:

1. Пустая строка может содержать пробельные символы (табуляции и т. Д.). fgets() подберет их. Но ваши вызовы strtok() не будут принимать пробельные символы, отличные от символа пробела.

2. @alk Я попробовал «rt». Но это все равно не работает…

3. @Gareth lam — Ваша программа отлично работает с GCC после исправления.

4. @Peter Вот почему я установил условный оператор для вывода «Пустой строки!» вместо обработки strtok() при встрече с пустой строкой. Пустая строка в . Файл DAT создается нажатием кнопки «Enter».

5. @alk "rt" ? А? Это какое-то странное расширение компилятора? Предполагается, что текстовый режим используется по умолчанию, если "b" он опущен.

Ответ №1:

Используйте if(line[0] != 'r' amp;amp; line[0] != 'n') вместо if(line[0] != 'n') .

Комментарии:

1. А? Операционная система использует это, а не strcmp() .

2. Я не вижу вызова strcmp() .

3. Извините, я перешел с strcmp() на строку [0] != ‘n’ . Но я обнаружил, что оба они имеют одинаковый результат, который равен «(null) 10 100».

4. @GarethLam Какой компилятор использовать?

5. @M.SChaudhari Спасибо за вашу помощь!

Ответ №2:

Пустая строка может содержать пробелы. Вы могли бы написать функцию для пропуска начальных пробелов. Или вы могли бы использовать sscanf() , который автоматически игнорирует пробелы. Это также позволяет считывать числа непосредственно в целые числа и числа с плавающей запятой.

 int field1;
double field2;

char line[100];
while(fgets(line, 100, fp)!=NULL)
{
    int num_matches = sscanf(line, "%d %lf", amp;field1, amp;field2);

    if( num_matches == 2 ){
        printf("%d %.2lfn", field1, field2);
    }
    else
    {
        printf("Malformatted linen");
    }
}
fclose(fp);