使用
scanf("%d",&rows)
而不是
scanf("%s",input)
这样可以直接从标准输入中获取整数值,无需转换为int类型。
如果用户输入的字符串包含非数字字符,则在下一个
scanf("%d",&rows)
之前需要清除标准输入。
你的代码可能如下所示:
#include <stdio.h>
#include <stdlib.h>
int clean_stdin()
{
int c;
while ((c = getchar()) != '\n' && c != EOF)
;
return 1;
}
int main(void)
{
int rows =0;
char c;
do
{
printf("\nEnter an integer from 1 to 23: ");
} while (((scanf("%d%c", &rows, &c)!=2 || c!='\n') && clean_stdin()) || rows<1 || rows>23);
return 0;
}
解释
1)
scanf("%d%c", &rows, &c)
这意味着期望用户输入一个整数,并紧跟一个非数字字符。
示例1:如果用户输入aaddk
,然后ENTER
,scanf将返回0。没有捕获到任何内容
示例2:如果用户输入45
,然后ENTER
,scanf将返回2(捕获了2个元素)。这里%d
捕获了45
,%c
捕获了\n
示例3:如果用户输入45aaadd
,然后ENTER
,scanf将返回2(捕获了2个元素)。这里%d
捕获了45
,%c
捕获了a
2)
(scanf("%d%c", &rows, &c)!=2 || c!='\n')
在示例1中:这个条件是TRUE,因为scanf返回0(!=2)
在示例2中:这个条件是FALSE,因为scanf返回2并且c == '\n'
在示例3中:这个条件是TRUE,因为scanf返回2并且c == 'a'(!='\n')
3)
((scanf("%d%c", &rows, &c)!=2 || c!='\n') && clean_stdin())
clean_stdin()
始终为TRUE
,因为该函数始终返回1
在示例1中: (scanf("%d%c", &rows, &c)!=2 || c!='\n')
为TRUE
,因此需要检查&&
后面的条件,因此将执行clean_stdin()
,整个条件为TRUE
在示例2中: (scanf("%d%c", &rows, &c)!=2 || c!='\n')
为FALSE
,因此不会检查&&
后面的条件(无论其结果如何,整个条件都将为FALSE
),因此不会执行clean_stdin()
,整个条件为FALSE
在示例3中:条件
(scanf("%d%c", &rows, &c)!=2 || c!='\n')
为
TRUE
,所以在
&&
之后的条件应该被检查,这样
clean_stdin()
将被执行,并且整个条件为
TRUE
。
因此,你可以注意到只有当用户输入包含非数字字符的字符串时,
clean_stdin()
才会被执行。
而且,这个条件
((scanf("%d%c", &rows, &c)!=2 || c!='\n') && clean_stdin())
只有当用户输入一个
整数
而没有其他内容时,才会返回
FALSE
。
如果条件
((scanf("%d%c", &rows, &c)!=2 || c!='\n') && clean_stdin())
为
FALSE
,且整数在
1
和
23
之间,则
while
循环将会终止;否则
while
循环将会继续。
while (count != rows);
。这会阻塞你的程序。 - MOHAMED"%[^\n]"
的意思是:期望输入一个字符串,其中包含除"\n"
(换行符)以外的任何字符。这意味着读取和清除标准输入的全部内容(感谢真主)。 - MOHAMEDinput
数组去掉了,用 char 类型的c
替换了它?!这是因为我们想尽可能地节省内存吗? - 7kemZmani