2010-09-04 81 views
2

我已經讀程序日誌文件中要做到這一點,我想用select()和read()選擇()不會等待

#include <stdlib.h> 
#include <string.h> 
#include <unistd.h> 
#include <sys/select.h> 
#include <fcntl.h> 
#include <stdio.h> 


int main() 
{ 
    int fd = -1; 
    fd_set fds; 
    struct timeval tv; 
    int rc; 
    char buffer[4096]; 
    char * log_path = "/home/mich/a.txt"; 
    if((fd = open(log_path,O_RDONLY)) == -1) 
    { 
     printf("error\n"); 
      return -1; 
    } 

    while(1) 
    { 

     FD_ZERO(&fds); 
     FD_SET(fd,&fds); 
     tv.tv_sec = 2; 
     tv.tv_usec = 0; 
     rc = select(fd+1, &fds, NULL, NULL, &tv); 

      if (rc < 0) { 
       printf("failed\n"); 
       continue; 
      } else if (rc > 0 && FD_ISSET(fd,&fds)) { 
       printf("read\n"); 
      } else { 
       printf("timeout\n"); 
       continue; 
      } 
     while ((my_getline(buffer,sizeof(buffer),fd)) > 0) 
     { 
      printf("%s",buffer); 
     } 
    } 
    close(fd); 
} 

my_getline是使用閱讀()的函數。

輸出:

read 
aaa 
read 
read 
read 
read 
read 
bbb 
read 
read 
read 
read 
... 

,其中aaa和bbb是從讀出的文件中的行。

這個程序有什麼問題?

+0

你期望你的程序做什麼? – ShiDoiSi 2010-09-04 12:39:05

+0

等待選擇新行,當他們看到他們閱讀。現在看來,選擇什麼都不做。 – mmatloka 2010-09-04 12:42:41

+0

你爲什麼要傳遞「fd + 1」來選擇?這聽起來不對。 – JesperE 2010-09-04 12:50:58

回答

2

select告訴你在fd上有什麼等待。這不必是一條線,它可以是單個字節,也可以是到達文件末尾的信息。在while循環的末尾添加puts("####");以查看代碼如何處理輸入文件。

要了解如何繼續讀取其他進程正在追加的文件,請查看unix tail實用程序(特別是其-f選件)的免費實現之一的源代碼。傳統的實現方式是讀取整個文件,休眠一小段時間(tail中的1秒),然後從最後一次讀取後離開的位置開始重複。更現代,更具反應性,更少資源,但便攜性更低的方法使用文件更改通知API(在Linux下kotue,* BSD下kqueue,...)。

4

select()告訴你read()不會阻塞。

這包括它將返回0以指示文件結束的情況,這可能是您所得到的結果。