1

xinetd 上的所有程序(我读过)都调用 fflush()。为什么?

例如,Inetd-维基百科

#include <stdio.h>
#include <stdlib.h>

int main(int argc, char **argv)
{
  const char *fn = argv[1];
  FILE *fp = fopen(fn, "a+");

  if(fp == NULL) 
    exit(EXIT_FAILURE);

  char str[4096];
  //inetd passes its information to us in stdin.
  while(fgets(str, sizeof(str), stdin)) {
    fputs(str, fp);
    fflush(fp);
  }
  fclose(fp);
  return 0;
}
4

2 回答 2

0

我认为您不需要在 fclose 之前调用 fflush。我看不出有任何理由在每次 fput 之后调用 fflush。基本上,当您需要同步某些操作时,您只需要 fflush ,但在大多数情况下,有更好的方法可以做到这一点。除非您是数据库开发人员或类似的人,否则您通常应该避免 IMO 使用 fflush。

如果您删除 fflush,程序也可以正常工作,即将 stdin 转储到文件并在退出时关闭文件。

另外,我认为它与inetd 或xinetd 没有任何关系。

正如在另一个答案中所写的那样,如果缓冲区被刷新,监视文件只会立即显示数据,但我认为在每次读取后刷新是一种不好的编程习惯。如果您想始终立即获取数据,最好使用:

setvbuf(fp, NULL, _IONBF, 0)

但即使这还不够,因为stdin数据源的缓冲未指定 AFAIK。您还需要设置它:

setvbuf(stdin, NULL, _IONBF, 0)

如果您想精确控制读/写行为并且不针对非 POSIX 平台,我相信您应该始终更喜欢 POSIX 函数而不是 ANSI 函数。POSIX 的语义open(),read()和比,和的语义write()简单得多。它只是在一个系统调用中读取/写入尽可能多的数据,并且除了您自己的缓冲区和内核套接字缓冲区之外没有任何缓冲,只要您请求它就可以为您提供数据。fopen()fread()fwrite()

于 2014-03-28T23:09:02.043 回答
0

fopen使用缓冲输入。也就是说,调用fputs将写入内存缓冲区,而不必将数据写入磁盘。调用fflush强制将输出缓冲区写入磁盘。

您的示例代码正在使用此模式,以便在通过套接字写入一些数据后立即写入文件,并且您可以监视文件以了解写入的内容。

于 2014-03-29T01:23:10.133 回答