如何在2分钟内限制程序在C语言中的执行
我没有任何代码,但假设用户应该在2分钟内回答数学问题并生成分数: 示例输出1:如何在2分钟内限制程序在C语言中的执行,c,C,我没有任何代码,但假设用户应该在2分钟内回答数学问题并生成分数: 示例输出1: 1+2 = *user's answer* 1+5 = *user's answer* 5+6 = *user's answer* 9+0 = *user's answer* 5+8 = *user's answer* 2+9 = *user's answer* Time: 0:2:0:0
1+2 = *user's answer*
1+5 = *user's answer*
5+6 = *user's answer*
9+0 = *user's answer*
5+8 = *user's answer*
2+9 = *user's answer*
Time: 0:2:0:0
Time's up!
Your score: 6
样本输出2:
1+2 = *user's answer*
1+5 = *user's answer*
5+6 = *user's answer*
9+0 = *user's answer*
Time: 0:2:0:0
Time's up!
Your score: 4
代码:
void add()//添加
{
int x,num,num2,ans,sum,score=0;
时间;
clrsc();
对于(x=0;x您不能使用标准设施。输入功能会一直阻塞,直到您收到输入,然后才能再次执行代码。因此,您有两个选项:
在等待输入之前花点时间。收到输入后,再花点时间,如果用户花的时间太长,则拒绝回答
使用不同的输入系统。例如,您可以使用Boost.Asio来实现,尽管它并不简单
假设一个与POSIX非常相似的系统,您可以使用
或(更好)
.概述:
static volatile sig_atomic_t alarmed = 0;
static void alarm_handler(int signum)
{
signal(signum, alarm_handler); // Uses signum — probably not strictly necessary
alarmed = 1;
}
...
signal(SIGALRM, alarm_handler);
alarm(2*60);
if ((nbytes = read(line, sizeof(line), STDIN_FILENO)) > 0)
{
...process normal answer...
}
else if (nbytes == 0)
...process EOF...
else if (errno == EINTR)
...check whether alarm went off — alarm_handler should set a flag...
else
...something broke — report error...
考虑到您可能正在使用标准I/O,您可以将read()
更改为fgets()
,并使用feof()
检查EOF,您可以假设您得到了一个错误,而不会造成任何麻烦ferror()
并执行errno
检查。在调用I/O函数之前,您可能更愿意将errno
设置为0;但严格来说这不是必需的
通过调用报警(0);
,您可以在任何时候取消报警呼叫
我在我的一个名为timeout
的程序中进行了深入研究,该程序运行另一个命令并等待它完成,但如果它没有足够快地完成,则会超时。注释中有一些注释可能对您有所帮助:
/*
** On MacOS X, the signal() function is implemented using sigaction()
** and includes SA_RESTART in the options, so that when the alarm times
** out, the signal catcher is called but wait() resumes, which is
** not what's wanted. Hence, upgrade to use sigaction() directly (when
** available; assume it is available by default) without the SA_RESTART.
*/
static void set_interruptible_alarm_handler(void (*handler)(int))
{
#ifdef NO_SIGACTION
/* Unlikely to be necessary on modern POSIX systems */
signal(SIGALRM, catcher);
#else
struct sigaction act;
if (sigemptyset(&act.sa_mask) != 0)
err_syserr("sigemptyset failed: ");
act.sa_handler = handler;
act.sa_flags = 0;
if (sigaction(SIGALRM, &act, 0) != 0)
err_syserr("failed to set signal handler\n");
#endif /* NO_SIGACTION */
}
使用sigaction()
比signal()
更详细,但控制效果更好。正如您所说,您使用的是Turbo C,您可以使用kbhit()
这是一个不可移植的功能,但在Turbo C世界中,它将返回最近按下的键,或零
因此,您可以将其放入检查当前时间的循环中,并检查是否按了键。请正确缩进您的代码。确定:)对不起,我只是不熟悉这一点。从代码的外观来看,您使用的是非常旧的编译器(可能是Turbo C或类似的编译器)。如果您使用较新的工具,您将获得更好的结果。可能重复的是,这是我的教授要求我们使用的。也可以通过创建单独的计时线程并使其中断输入线程来完成。这不会在我的编译器中运行:(还有其他不复杂的选项吗?@JasminAlarilla,遗憾的是,没有。@SebastianRedl您不能调用来自用户空间的信号让内核中断线程?请参阅警报,它会在这么多秒后生成SIGALRM
。谢谢..我希望它会运行:)非常感谢
/*
** On MacOS X, the signal() function is implemented using sigaction()
** and includes SA_RESTART in the options, so that when the alarm times
** out, the signal catcher is called but wait() resumes, which is
** not what's wanted. Hence, upgrade to use sigaction() directly (when
** available; assume it is available by default) without the SA_RESTART.
*/
static void set_interruptible_alarm_handler(void (*handler)(int))
{
#ifdef NO_SIGACTION
/* Unlikely to be necessary on modern POSIX systems */
signal(SIGALRM, catcher);
#else
struct sigaction act;
if (sigemptyset(&act.sa_mask) != 0)
err_syserr("sigemptyset failed: ");
act.sa_handler = handler;
act.sa_flags = 0;
if (sigaction(SIGALRM, &act, 0) != 0)
err_syserr("failed to set signal handler\n");
#endif /* NO_SIGACTION */
}