【问题标题】:Why can I not use fscanf() to read consecutive characters from a file?为什么我不能使用 fscanf() 从文件中读取连续字符?
【发布时间】:2019-02-24 05:19:17
【问题描述】:

我正在尝试使用以下代码编写一个程序来计算文件中的行数..

#include <stdio.h>

int main(int argc,char *argv[])
{
if(argc!=2)
{
  printf("invalid no. of arguments\nUsage:lc <FILENAME>\n");
  return 1;
}


FILE *in=fopen(argv[1],"r");

char c;
int count=0;
fscanf(in,"%c",&c); //take the first character

while(c!=EOF)
{
  if(c=='\n')
   count++;
   fscanf(in,"%c",&c);
}
fclose(in);

printf("TOTAL LINES:%d\n",count);
return 0;
}

我知道这可以通过使用 fgetc() 来实现,但我很想知道为什么 fscanf() 在这里不起作用。

非常感谢所有帮助。

【问题讨论】:

  • 您的缩进错误且令人困惑。 fscanf 返回您忘记测试的项目计数。最后,特别是在 Linux 上,stdinline 缓冲的。阅读how to debug small programs
  • EOF 不是char 它是int

标签: c file scanf


【解决方案1】:

您忘记测试fscanf 的结果计数。特别是当处理的文件是空文件时,你的程序是完全错误的。

while(c!=EOF)

永远不会发生(在任何fscanf(in,"%c",&amp;c)...之后)。 EOF 不是 一个有效字符(因此根据定义,它在 char 的所有可能值之外)。例如,在你的系统上,char 可能是无符号的 8 位,EOF 可能是 -1(EOF 记录在 -in §7.21.1 of the C11 standard- 是一些负数 int ,而不是一些char)。所以EOF 的类型不是char。在我的 Linux/Debian/x86-64 上发生了这种情况。

仔细阅读与&lt;stdio.h&gt;相关的documentation

一般来说,请阅读您正在使用的每个函数的文档。并学习How to debug small programs

这可以通过使用 fgetc() 来实现

是的,你最好使用fgetc。再次,阅读它的文档。 fgetc 很可能比fscanf 快得多(因为更底层)。 fscanf 的大多数实现都在使用 fgetc(或其等效项)。

最后,一些C standard library 实现free software。在 Linux 上,GNU glibcmusl-libc 都是。你可以研究他们的源代码。这样做你会学到很多东西。两者都是在 Linux syscalls(2) 之上构建的。

【讨论】:

  • 更糟糕的是,它不在char 的所有可能值之外。只需unsigned char
  • 不,如果charsignedunsigned(两者都发生),标准中没有指定。但是EOF 不是有效的char;在有符号 8 位 char 的实现上,EOF 不能为 -1(这将是一个 valid char)但可以是 +128(这不是一个有效的 char )
  • 是的,我对这里的任何事情都没有异议,但如果我正确阅读6.3.1.1 Boolean, characters, and integers(p2),它似乎有一点灰色区域。似乎该部分将明确允许char c; ... while (c != EOF) ...,因为"integer conversion rank" [char] "is less than or equal to the rank of int and unsigned int." 我不推荐它,但这是我看到的反驳论点。
  • @BasileStarynkevitch “它不在char 的所有可能值之外”与“标准未指定字符范围”并不矛盾。但是EOF 是负数所以不能是+128。
  • 请记住,EOF 来自失败的fscanf 的返回值也是...对于 +128 来说没有意义:D
猜你喜欢
  • 1970-01-01
  • 2014-02-10
  • 2013-05-04
  • 1970-01-01
  • 1970-01-01
  • 2017-05-03
  • 1970-01-01
  • 2017-06-25
相关资源
最近更新 更多