0

使用该feof()功能,在我的输出文件上,我将最后一个值打印了两次。我怎样才能避免这种情况?我的输出应该是

12
6
15
13

我有

12
6
15
13
13

谢谢!

while(!feof(pfile1))
{       
    sum=0;
    fscanf(pfile1,"%d%d%d",&choice,&day,&val);
    if(choice==0)
    {
        i=day-1;
        a[i]=a[i]-val;
    }
    else if(choice==1)
    {
        for(i=day-1;i<=val-1;i++)
        {
            sum=sum+a[i];

        }
        fprintf(pfile2,"%d\n",sum);     
    }
}
4

5 回答 5

1

这是因为 feof 标志只会在您读取 PAST 文件末尾时设置。要解决此问题,请将 feof 替换为下面的 fscanf 并检查参数的数量。

如果它低于 3,您就知道发生了一些错误......例如到达文件末尾。

事实上,出于上述原因,您应该尽可能避免使用 feof。

用一些代码强调这一点:

while(fscanf(pfile1,"%d%d%d",&choice,&day,&val) == 3) {
    //Continue reading
}
fclose(pfile1);
fclose(pfile2);
于 2012-08-22T07:45:54.063 回答
1

feof()发布的代码在处理不成功的读取之前不会检测到,从而导致您目睹的行为。

您需要feof()在调用后立即检查fscanf()或检查其结果fscanf()返回的分配数:

if (3 == fscanf(pfile1,"%d%d%d",&choice,&day,&val))
{
    /* All three integers successfully read. */
}

循环的另一种可能结构(如 MichalAnderson 的评论中所建议的):

while (3 == fscanf(pfile1,"%d%d%d",&choice,&day,&val))
{
}
于 2012-08-22T07:45:56.367 回答
1

一种选择是检查 的返回值fscanf

成功时,该函数返回成功读取的项目数。在匹配失败的情况下,该计数可以匹配预期的读数数量或更少 - 甚至为零。如果在成功读取任何数据之前输入失败,则返回 EOF。

所以,像:

if( fscanf(pfile1,"%d%d%d",&choice,&day,&val) <= 0 )
{
    break;
}

另一种选择是feof在执行后检查fscanf。例如:

if( feof( pfile1 ) )
{
    return; // or something
}
do
{
    // the same loop body
}
while( ! feof( pfile1 ) );
于 2012-08-22T07:46:46.167 回答
0

您应该检查读取元素的数量,如fscanf: 返回的那样,如果它不是您正在等待的 (3),您应该退出循环。

在这种情况下,您只需在最后一个读取行上工作两次。

文档中

返回值

成功完成后,这些函数将返回成功匹配和分配的输入项的数量;

于 2012-08-22T07:46:19.783 回答
0
fscanf(pfile1,"%d%d%d",&choice,&day,&val);

在这里,您正在从输入文件中读取整数。fscanf 将扫描文件,直到它到达 EOF。每次读取三个整数时,它都会返回 3 。如果 fsacnf 返回的值小于 3,那么它会自动分配缓冲区值。所以这就是在输出中获得重复值的原因。

如果通过检查 fscanf() 的返回值是否为 3 来编辑程序,然后执行有关选择的 if else 语句将给出所需的输出。

示例 1:-

考虑包含内容的输入文件:-

0 2 3

1 1 2

(--blank--) //这里 fscanf 将扫描一个整数,但由于它是一个空行,它将到达 EOF ,并返回 -1 并使用缓冲区值(以前的值)

然后输出文件: -

118

118

示例 2:-

输入文件(无空行):-

0 2 3

1 1 2

输出文件:-

118

于 2012-08-22T09:04:59.060 回答