Включить символ перевода строки при чтении с помощью fscanf - PullRequest
0 голосов
/ 09 октября 2018

Как я могу прочитать (n необязательный) символ новой строки при чтении файла слово за словом, используя fscanf()?

Я знаю, что мог бы использовать fgets() + strtok(), но моя программа специально требуетfscanf().

Я пробовал следующее:

fscanf(fp, "%s%[\n]+", buf);

Но это не работает вообще.

1 Ответ

0 голосов
/ 09 октября 2018

Вы можете использовать и игнорировать один символ новой строки с этим форматом преобразования: %*1[\n].Он потребляет не более одного символа новой строки и сбрасывает его.Обратите внимание, что если у вас есть несколько последовательных новых строк, будет пропущен только первый.Также обратите внимание, что fscanf() будет читать дополнительный байт, чтобы проверить, совпадает он или нет.Этот байт будет возвращен в поток с ungetc(), если он не совпадает.

Если вы использовали %*[\n], fscanf будет продолжать читать поток, пока он не получит байт, отличный от новой строки или не достигнетконец файла, который может вызвать неожиданное поведение при обработке интерактивного ввода с терминала.

Ваш код fscanf(fp, "%s[\n]", buf); вызывает неопределенное поведение, поскольку вы не предоставляете целевой массив для символов новой строки.Кроме того, у него есть еще один недостаток, поскольку вы не указываете максимальное количество байтов для хранения в buf, что приводит к неопределенному поведению при вводе с длинными словами.

Попробуйте это:

    char buf[100];
    if (fscanf(" %99s%*1[\n]", buf) == 1) {
        printf("read a word: |%s|\n", buf);
    } else {
        printf("no more words\n");
    }

Если вы хотите включить новую строку в буфер, вам нужно будет сохранить ее в переменной и добавить вручную:

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

int main() {
    for (;;) {
        char buf[100];
        char nl[2] = "";
        int n = fscanf(stdin, " %98s%1[\n]", buf, nl);
        if (n > 0) {
            strcat(buf, nl);
            printf("read a word: |%s|\n", buf);
        } else {
            printf("no more words\n");
            break;
        }
    }
    return 0;
}

Ввод:

Hello word
  I     am   ready    

Вывод:

read a word: |Hello|
read a word: |word
|
read a word: |I|
read a word: |am|
read a word: |ready|
no more words
...