为什么这个语句在while循环中打印两次?

我写了这个简单的练习程序:

#include  #include  #include  #define CLASSES 3 #define STUDENTS 4 int grades[CLASSES][STUDENTS]; int main(void) { int i = 1; char t,k; while(i == 1) { printf("\n\n\nMENU:\nEnter the grades(E)\nReport Grades(R)\nQuit(Q)\nYour choice: "); k = toupper(getchar()); printf("Input entered... %c\n", k); switch(k) { case 'E' : printf("Entering the grades..\n"); break; case 'R' : printf("Reporting the grades...\n"); break; case 'Q' : printf("Quitting the program...\n"); exit(0); break; default: printf("ERROR: %c: Incorrect menu option\n", k); break; } } return 0; } 

当我运行它时,它首先要求我输入一个选项。 如果我输入’E’或’R’,它会进入相应的’case’块,但是在while循环中的下一次迭代中,它不会等我输入我的选择。 相反,它假设我输入“NULL”并第三次询问我的提示。 每次进入选择时都会发生这种情况。 这是该程序的输出。 我在这里想念的是什么?

 host-mb:c_practice host$ ./asd MENU: Enter the grades(E) Report Grades(R) Quit(Q) Your choice: E Input entered... E Entering the grades.. MENU: Enter the grades(E) Report Grades(R) Quit(Q) Your choice: Input entered... ERROR: : Incorrect menu option MENU: Enter the grades(E) Report Grades(R) Quit(Q) Your choice: R Input entered... R Reporting the grades... MENU: Enter the grades(E) Report Grades(R) Quit(Q) Your choice: Input entered... ERROR: : Incorrect menu option MENU: Enter the grades(E) Report Grades(R) Quit(Q) Your choice: Q Input entered... Q Quitting the program... host-mb:c_practice host$ 

这是因为您键入一个字母,然后按Enter键。 使用另一个getchar()来获取尾随换行符。

所以改变这个:

 k = toupper(getchar()); 

对此:

 k = toupper(getchar()); getchar(); // eat the trailing newline 

当用户输入内容时,它会转到stdin (标准输入)流,系统会确保存储用户在内部缓冲区中输入的内容。 所以这是你的代码发生了什么:

在此处输入图像描述

所以解决方案是吃尾随换行


复活节彩蛋提示:

你应该收到这个:

 warning: implicit declaration of function 'printf' 

因为你缺少IO头,所以你应该在主文件的顶部添加:

 #include  

同样你应该添加:

 #include  // for toupper() #include  // for exit() 

另一个解决方案是使用fgets() ,看看这个问题更多C – scanf()vs gets()vs fgets() 。


我有一个类似的问题,你的scanf()和我在你的鞋子,所以我当时写下了解决方案 。