Linux 超时功能
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/7226603/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Timeout Function
提问by Hit's
I want to make a code in which Name of User will be asked to input, but in a time limit of 15 seconds. If user cross the limit & failed to input a name(or any string), then code will be terminated & "Time Out" Massage will be display otherwise Name should be saved & "Thanks" massage will be display. I had try like this but it's wrong & not working. Please give me a solution for this.. Thanks.
我想制作一个代码,其中将要求输入用户名,但时间限制为 15 秒。如果用户超过限制且未能输入名称(或任何字符串),则代码将终止并显示“超时”按摩,否则应保存名称并显示“谢谢”按摩。我曾尝试过这样但它是错误的并且不起作用。请给我一个解决方案..谢谢。
#include <stdio.h>
#include <time.h>
int timeout ( int seconds )
{
clock_t endwait;
endwait = clock () + seconds * CLOCKS_PER_SEC ;
while (clock() < endwait) {}
return 1;
}
int main ()
{
char name[20];
printf("Enter Username: (in 15 seconds)\n");
printf("Time start now!!!\n");
scanf("%s",name);
if( timeout(5) == 1 ){
printf("Time Out\n");
return 0;
}
printf("Thnaks\n");
return 0;
}
采纳答案by Shrey
Probably this dummy program might help you:
可能这个虚拟程序可能会帮助你:
#include <stdio.h>
#include <unistd.h>
#include <sys/time.h>
#include <sys/types.h>
#define WAIT 3
int main ()
{
char name[20] = {0}; // in case of single character input
fd_set input_set;
struct timeval timeout;
int ready_for_reading = 0;
int read_bytes = 0;
/* Empty the FD Set */
FD_ZERO(&input_set );
/* Listen to the input descriptor */
FD_SET(0, &input_set);
/* Waiting for some seconds */
timeout.tv_sec = WAIT; // WAIT seconds
timeout.tv_usec = 0; // 0 milliseconds
/* Invitation for the user to write something */
printf("Enter Username: (in %d seconds)\n", WAIT);
printf("Time start now!!!\n");
/* Listening for input stream for any activity */
ready_for_reading = select(1, &input_set, NULL, NULL, &timeout);
/* Here, first parameter is number of FDs in the set,
* second is our FD set for reading,
* third is the FD set in which any write activity needs to updated,
* which is not required in this case.
* Fourth is timeout
*/
if (ready_for_reading == -1) {
/* Some error has occured in input */
printf("Unable to read your input\n");
return -1;
}
if (ready_for_reading) {
read_bytes = read(0, name, 19);
if(name[read_bytes-1]=='\n'){
--read_bytes;
name[read_bytes]='##代码##';
}
if(read_bytes==0){
printf("You just hit enter\n");
} else {
printf("Read, %d bytes from input : %s \n", read_bytes, name);
}
} else {
printf(" %d Seconds are over - no data input \n", WAIT);
}
return 0;
}
Update:
This is now tested code.
更新:
这是现在测试的代码。
Also, I have taken hints from man for select. This manual already contains a code snippet which is being used to read from the terminal and timeout in 5 seconds in case of no activity.
另外,我从 man 那里得到了提示select。本手册已经包含一个代码片段,用于在没有活动的情况下从终端读取并在 5 秒内超时。
Just a brief explanation in case the code is not well written enough:
如果代码写得不够好,请简要说明:
- We add the input stream (
fd = 1) to the FD set. - We initiate
selectcall to listen to this FD set created for any activity. - In case any activity occurs within the
timeoutperiod, that is read through thereadcall. - In case there was no activity, timeout occurs.
- 我们将输入流 (
fd = 1)添加到 FD 集。 - 我们发起
select呼叫以收听为任何活动创建的此 FD 集。 - 如果在此
timeout期间发生任何活动,则通过read调用读取。 - 如果没有活动,则会发生超时。
Hope this helps.
希望这可以帮助。
回答by mouviciel
scanf()is not the best function to get an input in a limited time frame.
scanf()不是在有限的时间范围内获得输入的最佳功能。
Instead I would build a specific input function around select()(for managing timeout) and read()(for getting input) system calls.
相反,我会围绕select()(用于管理超时)和read()(用于获取输入)系统调用构建一个特定的输入函数。
回答by Didier Trosset
One thing you have to think about, is that you have a single thread of execution in your program. As such, the timeoutfunction will only be called when the scanffunction will be terminated. This is not what you want.
您必须考虑的一件事是,您的程序中只有一个执行线程。因此,timeout只有在scanf函数终止时才会调用该函数。这不是你想要的。
One way to do this task, is to use the selectfunction. It waits for a potentially limited amount of time (your timeout) for availability of input on some file descriptors (stdinfor you).
完成此任务的一种方法是使用该select功能。它等待可能有限的时间(您的超时)以获取某些文件描述符(stdin为您)的输入。

