fgets 用于逐行读取文件

10

我理解fgets函数会读取到EOF或者换行符。

我写了一个简单的代码来从文件中读取行,但是我观察到fgets执行的次数比期望的多。这个文件很简单,只有两个空行,即我按下一次回车并保存了文件。

以下是代码:

fp = fopen("sample.txt","r");
while (!feof(fp)) {
        fgets(line,150,fp);
        i++;
        printf("%s",line);
}
printf("%d",i);

为什么 while 循环会执行三次,而文件中只有两个空行?


如果您使用的是Linux系统,请尝试输入od -c sample.txt - Marian
我看到这个命令有四行...虽然文件中只有两行,即只看到了两个\n..@Marian - codeara
我找到了这个链接,它解释了同样的问题,但我仍然没有搞清楚。如果fgets第三次读取NULL,为什么会重复上一行?此外,如果它读取了第二行,缓冲区应该被清除,对吧?@Marian - codeara
1个回答

19
在你的情况下,最后一行似乎被读取了两次,但实际上并没有。对于fgets的最后一次调用返回NULL以指示已经读取完文件。你没有检查这个并再次打印缓冲区的旧内容,因为缓冲区没有更新。
通常最好不要使用feof,而是检查f...函数族的返回值:
fp = fopen("sample.txt", "r");
while (1) {
        if (fgets(line,150, fp) == NULL) break;
        i++;
        printf("%3d: %s", i, line);
}
printf("%d\n",i);

feof函数在尝试读取文件末尾之后返回true,这仅会在您最后(不成功的)fgets调用尝试读取文件末尾或者准确来说是在文件末尾之前时发生。在这个长的 SO 帖子中有更详细的解释。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接