一、feof的定义
feof()是检测流上的文件结束符的函数,如果文件结束,则返回非0值,否则返回0;
原型:int feof ( FILE * stream );
一般在操作中,经常用feof()判断文件是否结束。检查是否设置了与流关联的文件结束指示符,如果返回,则返回一个不同于零的值。该指示符通常由尝试在文件末尾读取的流上的先前操作设置。注意,流的内部位置指示符可能指向下一个操作的文件结尾,但是,直到操作试图在该点读取之前,文件结尾指示符可能才被设置。可以通过调用clearerr,倒带,fseek,fsetpos或freopen清除此指示符。尽管如果这样的调用未重新定位位置指示器,则下一个I / O操作可能会再次设置指示器。
二、经典用法
* feof example: byte counter */
#include <stdio.h>
int main ()
{
FILE * pFile; //用于存储文件地址
int n = 0; //计数
pFile = fopen ("myfile.txt","rb");
if (pFile==NULL) perror ("Error opening file");
else
{
while (fgetc(pFile) != EOF) {
++n;
}
if (feof(pFile)) {
puts ("End-of-File reached.");
printf ("Total number of bytes read: %d\n", n);
}
else puts ("End-of-File was not reached.");
fclose (pFile);
}
return 0;
功能分析:此代码将打开名为myfile.txt的文件,并通过逐个读取所有字符来计算其中包含的字符数。程序检查是否到达文件末尾,如果达到,则打印读取的字节总数。
三、经典错误
#include<stdio.h>
int main(void)
{
FILE *p;
p = fopen("open.txt", "r");
if (feof(p))
{
printf("文件为空。");
}
else
{
printf("文件不为空。");
}
return 0;
}
**分析:**根据这个函数的定义,一般大家都是这样使用的,但是这样使用,文件中无论是否有内容,都会被判断为“文件不为空”(跟文件打开方式也有关)。
四、feof()原理
1.EOF(宏定义)
EOF是一个计算机术语,为End Of File的缩写,在操作系统中表示资料源无更多的资料可读取。
资料源通常称为档案或串流。通常在文本的最后存在此字符表示资料结束。
在文档的结尾都有一个隐藏字符”EOF”,当程序读取它的时候,就会知道文件已经到达结尾。通常使用while循环加EOF判断作为读取结束的标志。
EOF 的值通常为 -1,但它依系统有所不同。
2.feof()
- feof()原理函数:,并不是通过读取到文件的EOF来评判,这个文件是否为空。对feof()来说,它的工作原理是,站在光标所在位置,向后看看还有没有字符。如果有,返回0;如果没有,返回非0。它并不会读取相关信息,只是查看光标后是否还有内容。
- 直接使用时:对于一个空文件来说,当程序打开它的时候,它的光标会停在文件的开头,但是由于文件里什么内容都没有存(但是EOF是存在的),即整个文件就存贮了一个EOF。当程序打开文件,并直接调用feof()时,这个函数就会站在光标的位置向后张望,结果就看见了EOF,然后就当然返回0了。
五、上程序改正
#include<stdio.h>
int main(void)
{
FILE *p;
p = fopen("open.txt", "r");
getc(p);
if (feof(p))
{
printf("文件为空。");
}
else
{
rewind(p);//将光标跳回到文件开头
int a;
fscanf(p,"%d",&a);
printf("%d", a);
}
return 0;
}
总结:
- 对于文件来说,无论是空文件,还是存有信息的文件,当文件被打开,光标处于默认的开头时,光标后都有信息,这时候调用feof()来查看光标后是否还有内容,就没意义。
- 所以我们需要从相同中找不同,先使用getc(),从文件中读取一个字符,让光标向后移动一个字符。这时空文件的光标就已经移动到EOF的后面,这时使用feof()就会返回1了。这才是feof()的正确用法。
- 但是要注意,一定要将光标回到文件的开头,因为之前判断文件是否为空时,将光标向前移动了一位,必须要将光标恢复到开头,这样才能保证文件的正常读取。