Как читать пустую строку в C - PullRequest
3 голосов
/ 30 апреля 2010

У меня проблема с чтением пустой строки в C. Я хочу прочитать строку из следующего -

  1. жопа
  2. мяч
  3. (пусто)
  4. кошка

но когда я использую gets(), он не обрабатывает (empty) как строку [2]. Он читает «кошка» как строку [2]. Так как я могу решить эту проблему?

char str1[15002][12];
char str2[15002][12];
char s[25];
map<string,int> Map;

int main()
{
    int ncase, i, j, n1, n2, count, Case;

    freopen("input.txt","r",stdin);
    freopen("output.txt","w",stdout);

    scanf("%d",&ncase);

    Case = 1;
    while(ncase > 0)
    {
        Map.clear();

        //this is the necessery part
        scanf("%d %d\n",&n1,&n2);
        count = 0;

        printf("n1=%d n2=%d\n",n1,n2);
        for(i = 0; i < n1; i++)
        {
          gets(str1[i]);
        }

        for(i = 0; i < n2; i++)
        {
            gets(str2[i]);
        }

        //end of reading input

        for(i = 0; i < n1; i++)
        {
            for(j = 0; j < n2; j++)
            {
                strcpy(s,str1[i]);
                strcat(s,str2[j]);

                if(Map[s] == 0){
                    count += 1;
                    Map[s] = 1;
                }
            }
        }

        printf("Case %d: %d\n", Case, count);
        Case++;
        ncase--;
    }
    return 0;
}

и ввод может выглядеть как

Я дал код здесь. Ввод может быть как

line1>1
line2>3 3
line3>(empty line)
line4>a
line5>b
line6>c
line7>(empty)
line8>b

И я ожидаю

str1[0]=(empty).
str1[1]=a;
str1[2]=b;

и

str2[0]=c;
str2[1]=(empty);
str2[2]=b;




ОК, наконец-то я нашел проблему. Это линия

printf("n1=%d n2=%d\n",n1,n2);

, что создает проблему при получении ввода gets(). Вместо новой строки с целым числом n1, n2, я беру новую строку как ("%c",&ch), и тогда все в порядке.

Спасибо всем, кто мне ответил.

Ответы [ 4 ]

3 голосов
/ 30 апреля 2010

Скорее всего, строка содержит \r\n\0 (или \n\r\0 - никогда не запоминайте, что будет первым). \r\n - это новая строка в Windows, а \0 - завершающий символ строки.

Обычно, если первый символ строки \r или \n, вы читаете пустую строку. ПОЭТОМУ это должно работать на всех платформах:

char* string;
// initialize string and read something into it
if (strlen(string) == 0 || string[0] == `\r` || string[0] == `\n`)
  // string is empty

Обновление: Вы упоминаете, что используете gets и читаете из файла. Однако для последнего вам понадобится fgets, поэтому здесь есть некоторая путаница. Обратите внимание, что fgets включает завершающий символ новой строки в возвращаемой строке, а gets - нет.

Update3: Способ чтения из файла действительно сомнительный. Вы открываете стандартный ввод для чтения из файла - почему ??? Стандартная практика - это fopen файла, затем считывание из него с fscanf и fgets.

Update2: глупо нас (и умно @Salil :-). Вы говорите

это читается как "кошка" как string[3]

Так как массивы C индексируются с 0, string[3] содержит прочитанную четвертую строку! Третья строка хранится в string[2] - держу пари, она будет содержать пустую строку, которую вы ищете.

2 голосов
/ 30 апреля 2010

Прежде всего, не использовать получает !!!!!Это уязвимость переполнения буфера , поскольку вы не можете указать размер буфера назначения, и поэтому gets () может легко переполнить ваш буфер.Вместо этого используйте fgets () или getchar () .

Поскольку вы используете картуЯсно, что вы на самом деле используете код C ++.В этом случае, еще лучший подход - использовать библиотеки C ++ iostreams для ввода и вывода.

Теперь, когда я покончил с моей разглагольствованием, проблема в том, что ... получает - что, опять же, вы никогда не должны использовать - согласно спецификации, будет читать до новой строки«любой должен быть отброшен».Функция fgets () копирует новую строку в буфер назначения, давая вам желаемое поведение.

2 голосов
/ 30 апреля 2010

Вывод этого кода:

#include <cstdio>

int main ()
{
    int i = 0;

    char string [256];
    while (gets(string)) {
        ++i;
    }
    printf("%d\n", i);

    return 0;
}

Для этого ввода

a
b

d

Есть

4

Это означает, что gets () правильно читает все строки, что, в свою очередь, означает, что ваш код должен быть испорчен. Разместите здесь.

0 голосов
/ 30 апреля 2010

Если строки нет, как вы собираетесь ее читать?

Пожалуйста, дайте нам кусок кода:)

== Позднее редактировать ==

OK:

"gets () читает строку из stdin в буфер, на который указывает s, до завершающей строки или EOF, которую он заменяет на '\ 0'."

Так что в основном, если у вас есть:

символ х [3];

получает (х);

Тогда эта функция заполнит x [0] значением '\ 0'

Если вы прочитаете man-страницу, вы увидите, что получать не рекомендуется. Вместо этого используйте fgets

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...