У меня проблема с использованием scanf () для получения новой строки, если новая строка пришла после пробела - PullRequest
0 голосов
/ 03 октября 2019

Я хотел иметь возможность хранить массив строк. И то, как я это делал, было с петлей. Я получаю каждое ядро ​​с помощью scanf и получаю символ char, чтобы получить пробел и проверяю, не является ли символ новой строки разрывом цикла.

    for (int i = 0; i < 10; i++) {
        scanf("%50s", arrayofStrings[i]);

        ch = getchar();
        if (ch == '\n') break;
    }

Это работает в большинстве случаев. Но если у меня есть что-то вроде «Я есть» с пробелом до конца строки, оно не попадет на новую строку.

Я попытался добавить цикл while, чтобы пропустить любой «», но это не такработать так, как я хотел.

Ожидаемый результат состоит в том, что, если я наберу "I \ n", он все равно доберется до новой строки, прервет цикл и просто проигнорирует пробел.


Я изменяю свой код после предложений в комментариях.

char cha[500];
int index= 0;

    fgets(cha, 500, stdin);

    for (int i = 0; i < 10; i++)
    {
        for (int j = 0; j < 50; j++)
        {
            if (cha[j] != ' ' && cha[index] != '\0') {
                var[i][j] = cha[index];
                index++;
            }
            else {
                action[i][j] = '\0';

                index++;
                break;
            }
        }
        if (cha[index] == '\0') {
            break;
        }
    }

    action[strlen(*action)] = "\0";
    printf("%s", var[0]);

, если я напишу "Никого здесь нет"

var [0] не будет иметь никого.

Но когда я проверяю с помощью strcmp(var[0], "Nobody"), они оказываются не равными.

1 Ответ

1 голос
/ 03 октября 2019

Вы пытаетесь изобрести овальное колесо, когда круглые колеса уже существуют ... Библиотека C существует по причине: чтобы программисты не тратили время на общие, но утомительные задачи.

Здесь вы хотите:

  • читать строку текста, заканчивающуюся новой строкой: ok fgets - это путь
  • разделить строку на пробелы sscanf можно использовать или strspn- strcspn. Выбор зависит от вашего фактического варианта использования: sscanf лучше, если вы хотите извлечь определенное количество токенов, strspn - strcspn более мощный, если у вас большая строка и вы хотите избегать двойного использованияпамять для токенов.

Конечно, всегда можно проанализировать вручную , и мы часто использовали его, когда было доступно только strtok. Просто нужно некоторое время держаться подальше от клавиатуры, взять лист бумаги и карандаш и спокойно описать, что вам действительно нужно. Затем попробуйте это (все еще на бумаге) для различных входов, ища возможные угловые случаи. Когда это работает (на бумаге) и только затем , преобразуйте алгоритм в язык Си и протестируйте идентифицированные угловые случаи в отладчике. Если вы хотите создать код профессионального уровня, запишите контрольные примеры для обычного варианта использования и углового варианта. Если вы позже внесете изменения в свой код, тест немедленно покажет возможные регрессии.

Ваш текущий код (и отсутствие комментариев) показывает, что вы записали его, не задумываясь о том, что он действительно будет делать

Вот возможный псевдокод для синтаксического анализа:

Loop over the line one char at a time
  if in a word
    if a word character
      add the character to current word
    if a separator
      end the current word with a null
  if in separators
    if a word character
      add a new word and make it the current word
      add the character to that word
if in a word
  end the word with a null character

Я знаю, что есть много тестов, и вы должны знать, словом вы или нет, нопо крайней мере, это должно работать ...

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