feof() 在 C 文件处理中

feof() in C file handling

提问人:sud03r 提问时间:4/14/2010 最后编辑:sud03r 更新时间:4/14/2010 访问量:7430

问:

我正在逐字节读取二进制文件,我需要确定 eof 是否已达到。

feof() 不起作用,因为“EOF 仅在对不存在的字节发出读取请求时设置”。因此,我可以自定义check_eof如下:

if ( fread(&byte,sizeof(byte),1,fp) != 1) {
    if(feof(fp))
    return true;
}
return false;

但问题是,如果未达到 eof,我的文件指针会向前移动一个字节。 因此,解决方案可能是使用,然后将其置于正确的位置。ftell()fseek()

另一种解决方案可能是在一些临时存储中提前缓冲字节。

有更好的解决方案吗?

C 文件处理 FEOF

评论

1赞 James McNellis 4/14/2010
您需要将流 () 传递给 。fpfeof

答:

0赞 KevinDTimm 4/14/2010 #1

我不清楚,但如果您有兴趣在读取字节之前了解是否已达到 EOF,请将您的 feof() 测试放在 fread() 之前而不是之后。
实际上,如果我没看错的话,你甚至不想这样做:

return feof(fp) ? true : false;

评论

1赞 R Samuel Klatchko 4/14/2010
这不是工作方式。仅仅在文件的末尾是不够的;在返回 true 之前,必须尝试读取文件末尾。feoffeof
0赞 KevinDTimm 4/14/2010
正确。这并不意味着我的答案是错误的,只是无关紧要(OP 应该已经在过去读取 EOF 时发现了错误)
0赞 abelenky 4/14/2010 #2

我建议使用:

fseek(myFile, 0, SEEK_END);
fileLen = ftell(myFile);
fseek(myfile, 0, SEEK_SET);

当您第一次打开文件以确定长度时。然后将读取循环设置为永不读出末尾。你可以用它来弄清楚你在哪里,并与 fileLen 进行比较,以确定你还需要走多远。ftell

评论

1赞 KevinDTimm 4/14/2010
始终假设文件在读取时会改变大小 - 无论是大还是小。
3赞 Kristopher Johnson 4/14/2010 #3

我通常会做这样的事情:

int get_next_char(FILE* fp, char *ch)
{
    return fread(ch, sizeof(char),1, fp) == 1;
}

// main loop
char ch;
while (get_next_char(fp, &ch))
    process_char(ch);

if (!feof(fp))
    handle_unexpected_input_error(fp);

评论

0赞 caf 4/14/2010
我认为这是最好的建议 - 重构你调用的代码,这样它就不需要在尝试读取之前检查 eof(我想这实际上意味着提前缓冲一个字符)。
6赞 jamesdlin 4/14/2010 #4

如果你一次读取一个字节,习惯的方法是:fgetc

int c;
while ((c = fgetc(fp)) != EOF) {
   // Do something.
}

然后你就不需要处理.feof

评论

2赞 William Pursell 3/26/2011
您仍然需要处理 feof(或 ferror)。当循环终止时,您需要检查它是否因为到达文件末尾而终止,或者是否存在读取错误。唯一的方法是使用这些函数之一。(除非您不关心报告错误。
2赞 R Samuel Klatchko 4/14/2010 #5

最好构建你的代码,以便你尝试读取一些数据,如果由于到达文件末尾而读取不成功,你就在那里处理它(即参见 Kristopher Johnson 的答案)。

如果你非常讨厌这个,你可以用它来将单个字符返回到流中,它将在下一个读取调用中可用:ungetc

int c = fgetc(fp);
if (c == EOF)
{
    // handle eof / error
}
else
{
    ungetc(c, fp);

    // the next read call is guaranteed to return at least one byte

}