先看一段非常简单的程序:
#include <stdio.h>
int main(int argc, char** argv)
{
char buf[8193];
FILE* fp = fopen("tmp.bin", "wb+");
fwrite(buf, 1, 8192, fp);
fseek(fp, 0, 0);
fread(buf, 1, 8193, fp);
/* here, all are ok, feof(fp) returns !0
*/
printf("8193, feof(fp)=%d\n", feof(fp));
fseek(fp, 0, 0);
fread(buf, 1, 8192, fp);
/* should feof(fp) return 0 or not? a true implementation should return 0
but now it is eof
*/
printf("8192, feof(fp)=%d\n", feof(fp));
fclose(fp);
return 0;
}
怎样在第二种情况下(8192)取得正确的 feof ?
问题在于,只有当 fread requested < actual_read 时,下一个 feof 才会返回 true ,而不管 filepointer 是否达到了 fileend。
当 fread requested == actual_read 时并且 fileptr 也确实到了文件末尾,feof 却不会返回 true ,
这样的话,feof 基本上就相当于一个摆设,它的功能 fread 就完全可以实现,使用如下代码:
for(;;)
{
size_t bytes_read = fread(buf, 1, bytes_requested, fp);
if (bytes_read == bytes_requested)
{
/* do something 1*/
}
else if (bytes_read < bytes_requested)
{
/* do something 2*/
break;
}
}
根本就不需要 feof ! feof 能做的,fread 完全可以做,fread做不了的,feof也做不了!
feof 的唯一用处就是:当fread 时 bytes_read < bytes_requested 并且 下一个feof返回了false,这表明文件发生了一个错误:
for(;;)
{
size_t bytes_read = fread(buf, 1, bytes_requested, fp);
if (bytes_read == bytes_requested)
{
/* do something 1*/
}
else if (bytes_read < bytes_requested)
{
if (feof(fp))
{
/* now, it is end of file */
}
else
{
/* now, it is an error on fp */
}
break;
}
}
这样一来,feof 的这个唯一作用是用来检查文件错误,而非 end of file。这种情况下,使用 ferror 能更准确地表达意图:
for(;;)
{
size_t bytes_read = fread(buf, 1, bytes_requested, fp);
if (bytes_read == bytes_requested)
{
/* do something 1*/
}
else if (bytes_read < bytes_requested)
{
if (ferror(fp))
{
/* now, it is an error on fp */
}
else
{
/* now, it is end of file */
}
break;
}
}
然而,就是因为 stdio.h 中有一个 feof,让我错误地以为 feof 必定会在 filepointer 到达 fileend 时返回 true。就这么一个小小的误解,让我调了一天,才找到程序错误的真正原因。
分享到:
相关推荐
在探讨“feof函数多读一次问题分析”这一主题时,我们首先需要理解feof函数的基本功能以及它在文件读取过程中的作用。feof(File End Of File)函数是C语言标准库中的一个函数,用于检测文件指针是否到达了文件末尾...
2. **文件结束**:`fread()` 在读到文件末尾时也会返回0。如果试图读取超过文件实际长度的数据,返回值将是从当前文件位置到文件末尾的实际字节数。 3. **错误条件**:如果文件流有错误(比如打开失败、权限问题等...
总的来说,理解并正确使用`feof()`是PHP开发中处理文件的基本技能之一。确保在使用`feof()`时进行适当的错误检查和资源验证,可以提高代码的健壮性和可靠性。同时,熟悉其他文件操作函数和类,如`SplFileObject`,...
C语言读取文件流相关函数用法简介 C语言中读取文件流的相关函数用法简介是非常重要的知识点,对于...fread()函数和feof()函数是C语言读取文件流的基本函数,master这些函数可以帮助开发者更好地读取和处理文件流数据。
`fread` 函数用于从文件中读取数据,其基本语法为: ```c size_t fread(void *ptr, size_t size, size_t nmemb, FILE *stream); ``` `ptr` 指向接收读取数据的内存位置,`size` 定义每个元素的大小,`nmemb` 是要...
除了基本的读写操作,还有其他高级文件操作,如文件定位(`fseek()`)、文件状态检查(`feof()`、`ferror()`)、文件重命名(`rename()`)等。理解并熟练掌握这些操作对开发复杂的C语言程序至关重要,特别是涉及数据...
其基本语法为:size_t fread(void *ptr, size_t size, size_t nmemb, FILE *fp),其中ptr是读取的缓冲区,size是每个元素的大小,nmemb是元素个数,fp是文件指针。 15. fwrite()函数:向流中写指定个数的字符 ...
总结来说,C语言中的文件操作涉及到文件的打开、读取、写入和关闭,主要使用`fopen()`、`fread()`、`fwrite()`、`fscanf()`、`fprintf()`、`fseek()`、`ftell()`、`feof()`、`ferror()`和`fclose()`等函数。...
本文主要探讨了使用fopen、feof、fclose以及fgets和fread等函数来读取文件的基本步骤和注意事项。 首先,`fopen()`函数是PHP中打开文件的关键。它接受两个参数:文件路径和模式。例如,`fopen("myfile", "r")`会以...
5. **文件操作(File Handling)**:fopen、fclose打开和关闭文件,fread、fwrite读写二进制数据,fgets、fputs读写文本数据,feof检查是否到达文件结束。 6. **错误处理(Error Handling)**:errno全局变量记录...
* 文件块读:int FREAD(void *ptr, int n, int fileid); * 文件块写:int FWRITE(void *ptr, int n, int fileid); * 判断文件结束:int FEOF(int fileid); * 获取文件指针:long FGETPOS(int fileid); * 设置文件...
- `fopen` 打开文件,`fclose` 关闭文件,`fread` 和 `fwrite` 读写文件内容。 - `feof` 检查文件是否到达末尾,`ferror` 检查文件操作是否有错误。 7. 其他常用函数: - `exit` 结束程序,`abort` 强制终止程序...
`fopen`、`fclose`分别用于打开和关闭文件,`fread`、`fwrite`读写二进制数据,`fscanf`、`fprintf`进行格式化数据的读写,`fgetl`、`fgets`读取文件行,`ferror`检查错误,`feof`检测文件是否结束,`fseek`设置文件...
在文件IO中,还有一些其他的函数,例如fclose函数用来关闭文件,feof函数用来判断文件是否结束,fseek函数用来将文件指针移到指定的位置等。 文件IO是计算机系统中最基本的输入/输出操作之一,它提供了一些基本的...
#### 一、二进制文件处理的基本概念 在C语言中处理文件时,通常有两种模式:文本模式和二进制模式。这两种模式的主要区别在于对数据的解释方式不同。文本模式主要用于处理文本文件,而二进制模式则适用于所有类型的...
最基本的调用形式为:a=fread(fid)其中,fid 是从 fopen 中得来的文件标识。MATLAB 读取整个文件并将文件指针放在文件末尾处(在后面的 feof 命令介绍中有详细解释)。 其他相关函数 * ferror:用于获取文件打开...
- 使用 Workspace 浏览器也可以查看变量信息。 - `delete <文件名>`:从磁盘中删除指定文件。 - `which <文件名>`:查找指定文件的完整路径。 - `clear all`:清除工作空间中的所有变量和函数。 - `help <命令...
`fwrite()` 和 `fread()`,以及文件结束检测函数 `feof()`。 1. **_getch() 与 getch() 区别** 在C语言中,`getch()` 是用于从标准输入读取单个字符的函数,通常用于控制台程序中获取用户输入。带下划线的 `_getch...
接着,`fread`用于读取二进制数据文件,如`[A,COUNT]=fread(Fid,size,precision)`,`A`为数据矩阵,`COUNT`为读取的元素数,`size`和`precision`定义读取的大小和精度。`fwrite`则用于写入二进制数据,`fprintf`和`...