【问题标题】:Return value of fgets()fgets() 的返回值
【发布时间】:2014-03-07 21:27:09
【问题描述】:

我最近刚刚开始在C 中使用I/O。这是我的问题 -
我有一个文件,我从中读取了我的输入。然后我使用fgets() 在缓冲区中获取字符串,我以某种方式使用它。现在,如果输入对于缓冲区来说太短会发生什么,即如果fgets() 的第一次读取达到EOFfgets() 是否应该返回 NULL(正如我在 fgets() 文档中阅读的那样)?似乎没有,我得到了正确的输入。此外,即使我的feof(input) 也没有说我们已经到达EOF
这是我的代码 sn-p。

char    buf[BUFSIZ];
FILE    *input,
        *output;

input   = fopen(argv[--argc], "r");
output  = fopen(argv[--argc], "w");

/**
 *  If either of the input or output were unable to be opened
 *          we exit
 */
if (input == NULL) {
    fprintf(stdout, "Failed to open file - %s.\n", argv[argc + 1]);
    exit(EXIT_FAILURE);
}

if (output == NULL) {
    fprintf(stdout, "Failed to open file - %s.\n", argv[argc + 0]);
    exit(EXIT_FAILURE);
}

if (fgets(buf, sizeof(buf), input) != NULL) {
    ....
}

/**
 *  After the fgets() condition exits it is because, either -
 *      1) The EOF was reached.
 *      2) There is a read error.
 */
if (feof(input)) {
    fprintf(stdout, "Reached EOF.\n");
}
else if (ferror(input)) {
    fprintf(stdout, "Error while reading the file.\n");
}

【问题讨论】:

  • 请注意,feof(input) 只会在 尝试读取过去 EOF 之后返回true。它不会告诉你你在 EOF。
  • 你能在上面的例子中解释一下吗?假设,fgets() 只读取 100 bytesBUFSIZE 是 512),fgets() 是否应该返回 NULL
  • 好的,现在我意识到我的评论是多么愚蠢;反正我明白你的意思。如何检查是否达到 EOF?

标签: c io fgets


【解决方案1】:

fgets() 的文档并没有说明您的想法:

来自我的手册页

fgets() 从流中读取最多比size 少一个字符,并将它们存储到s 指向的缓冲区中。读 在 EOF 或换行符之后停止。如果读取了换行符,则将其存储到缓冲区中。存储终止空字节('\0') 在缓冲区中的最后一个字符之后。

后来

gets()fgets() 在成功时返回 s,在错误时或在未读取任何字符时出现文件结尾时返回 NULL

我不认为EOF 将被视为错误条件并返回NULL。事实上,它说 NULL 只会出现在 EOF 出现时,没有个字符被读取。

POSIX 标准(遵循较难访问的 C 标准)在这里:http://pubs.opengroup.org/onlinepubs/009695399/functions/fgets.html 并声明:

成功完成后,fgets() 应返回 s。如果流处于文件末尾,则应设置流的文件结束指示符,fgets() 应返回空指针。如果发生读取错误,则应设置流的错误指示符,fgets() 应返回空指针,并应设置errno 以指示错误。

这清楚地表明它只会在调用时返回NULL,如果它实际上在EOF,即如果读取任何个字节,它不会返回NULL

【讨论】:

  • 你能解释一下feof() 部分,为什么它不打印任何东西。 EOF 已到达对吗?
  • feof() 测试文件结束指示符,该指示符仅在您尝试读取文件末尾时出现错误时设置。它并不(令人困惑地)表明您在文件的末尾。
  • 你再次执行fgets(),你将得到EOF。这是正常的测试方式。
  • @yadav_vishal abligh 说了什么。您继续使用fgets,直到您看到它返回NULL 以结束循环。此时,feof 应该为 TRUE,因为 NULL 表示 fgets 试图读取 EOF。
  • 知道了!谢谢!我用了if(),应该用while()
猜你喜欢
  • 2017-07-24
  • 2013-03-30
  • 1970-01-01
  • 2018-05-19
  • 1970-01-01
  • 2018-05-23
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多