C语言 fflush(stdin) 的使用问题

C语言中,fflush() 函数的主要目的是刷新输出流,但在某些平台上,会使用 fflush(stdin) 来清空输入缓冲区。但是不建议使用 fflush(stdin) 来清空输入缓冲区,因为这种用法并不符合C标准,可能在不同平台上表现不同。

1、fflush() 的标准用法

根据C语言标准,fflush() 函数的语法如下,

int fflush(FILE *stream);

stream 是指向 FILE 对象的指针,通常是 stdoutstderr 或文件指针。fflush() 刷新指定流的缓冲区内容。对输出流来说,它会将缓冲区中的数据实际写入文件或设备。

2、fflush(stdin) 是未定义行为

根据C语言标准(C99及之后),fflush() 只能用于输出流(如 stdout),而不能用于输入流(如 stdin)。使用 fflush(stdin) 是未定义行为,也就是编译器和运行环境可以自由地决定如何处理 fflush(stdin),而结果可能因平台而异。

3、fflush(stdin) 会被使用的原因

在某些特定的平台(如一些旧版的Windows编译器),fflush(stdin) 被用作清除标准输入缓冲区的非标准方法。然而,这种用法并不是所有编译器都支持的,因此在跨平台编程时会产生不兼容问题。

4、清除 stdin 缓冲区推荐方法

为了跨平台地清除 stdin 缓冲区,可以使用以下几种推荐方法。

1)使用 getchar() 清空缓冲区

getchar() 逐个读取缓冲区中的字符,直到遇到换行符 \n 或文件结束符 EOF。如此可以确保清除 stdin 中残留的输入数据。

#include <stdio.h>

int main() {
    int c;
    printf("Enter a character: ");
    char ch = getchar();

    // 清空缓冲区中剩余的字符,直到遇到换行符或 EOF
    while ((c = getchar()) != '\n' && c != EOF) {
        // 空循环体,用于丢弃输入缓冲区中的字符
    }

    printf("You entered: %c\n", ch);
    return 0;
}

2)使用 scanf() 清空缓冲区

在格式字符串 " %c"中使用前导空格,scanf() 会跳过所有空白字符(如空格和换行符),直到遇到一个非空白字符。这种方法仅适用于需要读取一个字符的情况。

#include <stdio.h>

int main() {
    char ch;
    printf("Enter a character: ");
    scanf(" %c", &ch);  // 注意前面的空格,它可以跳过所有空白字符,包括换行符

    printf("You entered: %c\n", ch);
    return 0;
}

5、fflush(stdin) 替代方法使用示例

在处理用户输入时,需要在用户输入数字之后清除缓冲区中的其他字符,可以使用 getchar() 来替代 fflush(stdin)。

#include <stdio.h>

int main() {
    int num;
    printf("Enter a number: ");
    if (scanf("%d", &num) != 1) {
        printf("Invalid input.\n");
    }

    // 清空输入缓冲区中剩余的字符
    int ch;
    while ((ch = getchar()) != '\n' && ch != EOF) {
        // 丢弃剩余的输入字符
    }

    printf("You entered: %d\n", num);
    return 0;
}

推荐阅读
cjavapy编程之路首页