C - пытается прочитать один символ из стандартного ввода (и не удается) w / scanf / getchar - PullRequest
5 голосов
/ 24 декабря 2009

как часть домашнего задания, я пытаюсь прочитать один символ из стандартного ввода и действовать в соответствии с ним:

char choice;

while (1) {
    printf("please enter [y]es, [n]o or [m]aybe: ");
    scanf("%c", choice);
    fflush(stdin);
    // validate input
    if (choice == 'y' || choice == 'n' || choice == 'm') {
        break;
    } else {
      printf("Please enter only \'y\', \'n\' or \'m\'!\n");
    }
}
// do something with the input
if (choice == 'y') {
    printf("you selected yes!\n");
}

по какой-то причине, scanf захватывает как символ, так и перевод строки после, таким образом, он продолжает что-то делать со входом и затем выводит «Пожалуйста, введите только« y »,« n »или« m »!» линия. Если я введу несколько символов в stdin, он напечатает эту строку для всех из них, а также будет работать правильно для первого символа. Так, например:

$ ./run
please enter [y]es, [n]o or [m]aybe: y<return>
you selected yes!
Please enter only 'y', 'n' or 'm'!
$ ./run
please enter [y]es, [n]o or [m]aybe: yes<return>
you selected yes!
Please enter only 'y', 'n' or 'm'!
Please enter only 'y', 'n' or 'm'!
Please enter only 'y', 'n' or 'm'!
$

То же самое происходит, если я использую getchar. Что мне не хватает? спасибо.

Ответы [ 4 ]

9 голосов
/ 24 декабря 2009

Вам нужен пробел между scanf(" и %c, чтобы он работал правильно:

scanf(" %c", &choice);

И вам также нужно использовать & выбор, а не выбор!

РЕДАКТИРОВАТЬ: В то время как вы на это, вы можете посмотреть do while() для этого цикла (если профессор специально сказал, чтобы использовать break) - do while прекрасно работает при проверке ввода пользователя!

4 голосов
/ 24 декабря 2009

fflush () не определяется ISO для входных потоков. Он определен в библиотеке времени выполнения Microsoft C, но не является переносимым.

Хотя решение «пробел до% c» может работать, когда пользователь вводит ожидаемые данные, оно во многих случаях завершится сбоем; попробуйте ввести "да нет", например. Консольный ввод ориентирован на лин; Лучше всего убедиться, что вы сбрасываете всю линию таким образом:

scanf( "%c", choice ) ;
while( choice != '\n' && getchar() != '\n' ) /* do nothing*/ ;
3 голосов
/ 24 декабря 2009

Еще лучше, используйте fgetc (). scanf () всегда должен быть последним средством.

0 голосов
/ 14 ноября 2015

Прежде всего, я буду кратким. Из-за нехватки баллов, чтобы оставить комментарий Если мы можем видеть, что число o / p равно (один + номер символа) Это происходит, когда мы нажимаем клавишу ВВОД после ввода символов '\ n', непечатный символ также добавляется после вашей строки.

$ ./run
please enter [y]es, [n]o or [m]aybe: y<return>
you selected yes!
Please enter only 'y', 'n' or 'm'!  -----------> it is due to reading of the '\n' by scanf

EDITED Из-за недостатка баллов я мог бы опубликовать это в качестве комментария. Это обходной путь вышеупомянутых ответов

...