为了回到C编程的流程,我一直在打字一些简单的测试程序.我遇到了scanf函数的一个奇怪问题.我在下面的代码中有3个,但只有前2个被初始化; 第三个scanf被忽略.这是正常的,还是我做错了什么?我一直在盯着这段代码过去半小时,我找不到任何错误.
#include <stdio.h>
int math(int a, int b, char selection) {
int result;
switch (selection) {
case 'a':
result = a + b;
break;
case 's':
result = a - b;
break;
case 'm':
result = a * b;
break;
case 'd':
result = a / b;
break;
}
return result;
}
int main() {
int num1 = 0;
int num2 = 0;
int result = 0;
char selection;
printf("Enter first number: ");
scanf("%i", &num1);
printf("Enter second number: ");
scanf("%i", &num2);
printf("\n[a] Add\n[s] Subtract\n[m] Multiply\n[d] Divide\n\nWhich one: ");
scanf("%c", &selection);
result = math(num1, num2, selection);
printf("%i", result);
return 0;
}
Run Code Online (Sandbox Code Playgroud)
回答你的问题:
scanf函数可以使用多少次?
不,没有.
但这不是这里发生的事情.
当你做这样的事情:
printf("Enter second number: ");
scanf("%i", &num2);
Run Code Online (Sandbox Code Playgroud)
您实际上输入了两个值stdin,第一个是数字,第二个是不可见的换行符.
you can't see that, but it's there
V
> Enter second number: 3\n
Run Code Online (Sandbox Code Playgroud)
这种方式scanf()有效,它将读取并存储输入stdin到您的变量,直到它们全部填满,然后它将剩下其余部分.在我的示例中3存储到num2并'\n'保持打开stdin然后当此代码运行时:
scanf("%c", &selection);
Run Code Online (Sandbox Code Playgroud)
它将查找stdin并找到位于'\n'那里的换行符().这可以存储为字符类型,因此它将填充selection它.
解决此问题的一种方法是将代码更改为:
scanf(" %c", &selection);
Run Code Online (Sandbox Code Playgroud)
%告诉之前的空格scanf忽略stdin缓冲区开头的任何空格(包括换行符).
关于调试的旁注:
当您认为出现问题时,请使用调试器或打印一些值以给您信心和理解.例如,我会更新您的代码:
printf("\n[a] Add\n[s] Subtract\n[m] Multiply\n[d] Divide\n\nWhich one: ");
int ret = scanf("%c", &selection);
printf("Scanf I think failed. Return value is: %d. Selection is: %c (%d)\n",
ret, selection, selection);
Run Code Online (Sandbox Code Playgroud)
您可以从手册页中找到返回值的含义.在这种情况下,此处的返回代码将告诉您已成功匹配和分配了多少项.你在这里看到1,所以你知道这个电话有效.您的输出看起来像:
Scanf I think failed. Return value is: 1. Selection is:
(10)
Run Code Online (Sandbox Code Playgroud)
这告诉你scanf确实得到了一些东西,你没有看到打印的字符,但是输出跳过一行(可疑)并且打印的ASCII值是10 10,看起来你会看到它是一个换行符.