为什么fflush(stdin)不会删除缓冲区(stdin)

Hoa*_*inh -1 c macos

我有这样的测试代码

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

int main() {
    char c, str[20];
    printf("Enter a character : ");
    scanf("%c", &c);
    printf("Enter a string : ");
    fflush(stdin);
    gets(str);
    printf("\n\n\nResult : %c\n%s\n", c, str);
    return 0;
}
Run Code Online (Sandbox Code Playgroud)

我读过一些文章说这段代码会起作用,因为在扫描c字符后,缓冲区中仍然有'\n'字符.fflush(stdin)将清除缓冲区,因此gets()函数可以正常工作

但事实上,当我在Mac OS环境中编译并运行此代码时,fflush(stdin)什么都不做.我输入了一个字符(例如,'k'),然后它打印了k字符和'\n'字符.它假设允许我输入一个字符,一个字符串,然后打印它们.谁知道为什么?谢谢!

Bas*_*tch 8

fflush(3)被记录为处理输出流,而不是输入流.

标准未指定输入流的行为.

特别是POSIX规范fflush没有提到输入流.因此,从POSIX的角度来看,这可能是一种未定义的行为.

但是,在Linux上fflush(stdin)是可能的(但我不推荐它)

对于输入流,fflush()会丢弃从底层文件中提取但尚未被应用程序使用的任何缓冲数据.

BTW,gets(3)因为危险(可能的缓冲区溢出!)而被弃用,并且已经从C11标准中消失了.至少使用fgets(3)getline(3).也许考虑GNU readline库(它提供了很好的编辑能力).

  • 手册页与您相矛盾:"对于输入流,fflush()会丢弃从底层文件中提取但尚未被应用程序使用的任何缓冲数据." (2认同)