【问题标题】:How to abort getchar() command in C?如何在 C 中中止 getchar() 命令?
【发布时间】:2015-03-29 18:07:54
【问题描述】:

我基本上是一个初学者 C++ 程序员...这是我第一次尝试用 C 编写代码。

我正在尝试编写一个蛇游戏(使用system ("cls"))。

在这个程序中,我需要获取一个字符作为输入(基本上是为了让用户改变蛇的运动方向)......如果用户在半秒内没有输入任何字符,那么这个字符输入命令需要中止,我的剩余代码应该被执行。

请提出解决此问题的建议。

编辑:感谢您的建议,但是 我提出这个问题的主要动机是找到一种方法来中止 getchar 命令,即使用户没有输入任何内容......对此有什么建议吗?顺便说一句,我的平台是 windows

【问题讨论】:

  • C?目标-c? C++?请决定。无论如何,您需要使用 POSIX 或平台方法。
  • 您不应该使用system("cls") 来清除屏幕,它是不可移植的,并且它会产生一个全新的进程(或两个?)只是为了清除屏幕,因为符合 POSIX 的平台需要看看 ncurses。
  • 你为什么把它标记为目标C?这显然与 Objective C 无关。
  • 您可以使用_kbhit检查可用的键盘输入。
  • @eryksun 谢谢兄弟你的想法有效....你能把这个作为答案发布,这样我就可以通过接受它来结束这个问题。

标签: c windows console-application getchar


【解决方案1】:

在我看来,最好的方法是使用 libncurses。

http://tldp.org/HOWTO/NCURSES-Programming-HOWTO/

您拥有轻松制作蛇的所有工具。

如果你觉得太简单(它是一个比较高级的库),看看 termcaps 库。

编辑:因此,使用 termcaps 进行非阻塞读取是:

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

uintmax_t          getchar()
{
  uintmax_t        key = 0;

  read(0, &key, sizeof(key));
  return key;
}

int                main(int ac, char **av, char **env)
{
  char             *name_term;
  struct termios   term;

  if ((name_term = getenv("TERM")) == NULL) // looking for name of term
     return (-1);
  if (tgetent(NULL, &name_term) == ERR) // get possibilities of term
     return (-1);
  term.c_lflag &= ~(ICANON | ECHO);
  term.c_cc[VMIN] = 0; term.c_cc[VTIME] = 0; // non-blocking read
  if (tcgetattr(0, term) == -1) // applying modifications.
     return (-1);
  /* Your code here with getchar() */
  term.c_lflag &= (ICANON | ECHO);
  if (tcgetattr(0, term) == -1) // applying modifications.
     return (-1);
  return (0);
}

编辑 2: 您必须使用

进行编译

-攻击

选项。

【讨论】:

    【解决方案2】:

    在类 UNIX 平台(如 Linux)上执行此操作的方法是使用 select 函数。你可以找到它的文档online。我不确定这个功能在 Windows 上是否可用;你没有指定操作系统。

    【讨论】:

    • system("cls") 适用于 Windows;默认情况下它在 Linux 上不起作用。
    【解决方案3】:

    我在 cmets 中得到了最适合我的问题的答案,该答案由 @eryksun 发布。

    最好的方法是使用函数kbhit()(conio.h 的一部分)。

    【讨论】:

      【解决方案4】:

      您可以生成一个新线程,该线程可以模拟在 30 秒后按下 Enter 键。

      #include <windows.h>
      #include <stdio.h>
      #pragma comment(lib, "User32.lib")
      
      void ThreadProc()
      {
          // Sleep for 30 seconds
          Sleep(30*1000);
          // Press and release enter key
          keybd_event(VK_RETURN, 0x9C, 0, 0);
          keybd_event(VK_RETURN, 0x9C, KEYEVENTF_KEYUP, 0);
      }
      
      
      int main()
      {
          DWORD dwThreadId;
          HANDLE hThread = CreateThread(NULL, 0,(LPTHREAD_START_ROUTINE)ThreadProc, NULL, 0,&dwThreadId);
          char key = getchar();
          // you are out of getchar now. You can check the 'key' for a value of '10' to see if the thread did it. 
          // Kill thread before you do getchar again
      }
      

      小心使用这种技术,特别是如果你在循环中执行 geatchar(),否则你可能会得到很多线程按下 ENTER 键!确保在再次启动 getchar() 之前终止线程。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2013-09-05
        • 1970-01-01
        • 1970-01-01
        • 2014-12-02
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多