如何丢弃在睡眠功能期间传递的用户输入?

How do I discard user input delivered during sleep function?

我正在尝试使用终端创建游戏。我询问玩家是否准备好,然后使用下面的代码进行倒计时。问题是用户所做的所有输入都被添加到程序进行的下一个输入查询中。我正在寻找一种方法来丢弃之前的输入或在此函数期间完全阻止它。

我可以执行 getchar 循环,但我不希望在倒计时后(按回车键)需要用户输入。

void countdown(void){
  printf("5\n");
  sleep(1);
  printf("4\n");
  sleep(1);
  printf("3\n");
  sleep(1);
  printf("2\n");
  sleep(1);
  printf("1\n");
  sleep(1);
  clearScreen(0); //clears terminal
}

你基本上做不到; "discarding user input during a certain amount of time" 的概念对于标准输出和输入没有任何意义,例如考虑您的输入可能来自文件的事实(这里的问题是 'time' 实际上不是以任何方式存在于标准 in/output 例程中的概念)。

为此你需要一个终端 API,C 标准库中没有类似的东西,尽管有库提供这样的功能(但你已经说过你不想使用外部库)。

一种方法是使用线程进行倒计时。

主代码启动倒计时线程,然后循环获取输入。

如果线程终止之前输入函数returns,或者输入了错误的回复,则忽略输入并重复循环。

由于您使用的是linux环境,您可以尝试使用tcflush()

Link to tcflush documentation

这是使用 tcflush 修改代码的示例。您可以取消注释底部,并看到在倒计时期间输入的所有内容都已从 stdio 缓冲区中清除。

#include <termios.h>
#include <stdio.h>
#include <unistd.h>

void main(){
        char str[100];
        printf("5\n");
        sleep(1);
        printf("4\n");
        sleep(1);
        printf("3\n");
        sleep(1);
        printf("2\n");
        sleep(1);
        printf("1\n");
        sleep(1);

        // arguments for tcflush: 
        // 0 is for stdin 
        // TCIFLUSH is to flush data received but not read
        tcflush(0,TCIFLUSH);

        // prove it works by uncommenting this code
//      printf("fgets is waiting");
//      fgets(str, sizeof(str), stdin);
//      printf("%s", str);

//      clearScreen(0); //clears terminal
}