我是ANSI C的初学者,我有一个问题,这可能是一个愚蠢的问题,我很抱歉。
#include<stdio.h>
main()
{
int age;
printf("Hello World!\n");
printf("Please enter your age: ");
scanf("%d", &age);
printf("You entered %d\n", age);
fflush(stdin);
getchar();
}
这是我学习scanf功能的第二个程序。 我的问题是: 我知道 printf , scanf , fflush , stdin 和 getchar 已定义在 stdio.h ,但只有当我使用 fflush(stdin)时,我必须将 #include&lt; stdio.h &gt; ,但是当使用任何其他方法时,我可以删除该行#include。
答案 0 :(得分:9)
当您调用该标头中声明的任何函数时,必须 #include <stdio.h>
。
好的,那不是相当是真的。在1989/1990版本的语言标准中,调用可以创建函数的隐式声明。如果这恰好符合正确的声明,你就可以逃脱它;否则你的程序的行为是未定义的 - 这意味着你仍然可能侥幸逃脱它,但编译器不需要警告你。由于printf
采用可变数量的参数,因此必须具有可见的声明以避免未定义的行为 - 获取可见声明的方式为#include <stdio.h>
。
(你也可以自己声明这个功能,但这很容易出错,而且没有充分的理由去做。)
在C99及更高版本中,没有隐式声明。
main()
应为int main(void)
。
fflush(stdin)
有未定义的行为。如果您要放弃在scanf()
通话后输入的字符,您可以阅读并放弃它们。
答案 1 :(得分:2)
您可能需要该头文件,因此将定义stdin
。如果关闭编译器警告,编译器将不会让您知道未定义的函数。 (如果他们真的是
未定义,稍后您将收到链接器错误)。 stdin
是FILE *
类型的变量,而不是函数。
请不要致电fflush(stdin)
。它有未定义的行为。如果需要清除输入缓冲区,请使用其他方法。执行此操作的标准方法是尝试读取数据,直到下一行结束:
int flush_line(FILE *file)
{
int ch;
do {
ch = fgetc(file);
} while (ch != '\n' && ch != EOF);
if (ch == EOF && ferror(file)) {
return -1;
}
return 0;
}
然后你会打电话给flush_line(stdin)
。
如果不考虑可移植性(请注意,这不适用于Windows),您可以暂时使文件描述符无阻塞,并从中读取所有输入:
int flush_in(FILE *file)
{
int ch;
int flags;
int fd;
fd = fileno(file);
flags = fcntl(fd, F_GETFL, 0);
if (flags < 0) {
return -1;
}
if (fcntl(fd, F_SETFL, flags | O_NONBLOCK)) {
return -1;
}
do {
ch = fgetc(file);
} while (ch != EOF);
clearerr(file);
if (fcntl(fd, F_SETFL, flags)) {
return -1;
}
return 0;
}
然后你会打电话给flush_in(stdin)
。