如何摆脱那个"文本的结尾"

时间:2016-10-28 11:59:25

标签: c linux

我在C中编写一个小程序来反转输入文件的内容并写入输出文件。

#include <stdio.h>
#include <stdlib.h>
#define BS 12

int main (const int argc, const char** argv)
{
  if(argc != 3)
    exit(-1);

  unsigned char buffer[BS];
  FILE * f1, * f2;
  f1 = fopen(argv[1], "r");
  f2 = fopen(argv[2], "w");

  fseek(f1, 0, SEEK_END);

  long i = 0, j = 0;
  long f1_len = ftell(f1);
  unsigned char tmp;

 // while(i >= 0)
//  {
    for(i = ftell(f1), j = 0; i >= 0 && j <= BS - 1; i--, j++)
    {
      fseek(f1, i, SEEK_SET);
      tmp = fgetc(f1);

      if(i == f1_len || tmp == (unsigned char)0x03)
        continue;
      else
        buffer[j] = tmp;
    }
    if(j == BS - 1)
      fwrite(buffer, BS, 1, f2);
    else
      fwrite(buffer, j, 1, f2);

    fflush(f2);
 // }

  fclose(f1);
  fclose(f2);

    return 0;
}

testfile的:

$ xxd testfile
0000000: 6162 6364 6566 670a                      abcdefg.

试验:

$ gcc test.c -o test
$ test testfile testfile2
$ xxd testfile2
0000000: 030a 6766 6564 6362 61                   ..gfedcba

为什么有&#39; 0x03&#39;?我已经写了tmp == (unsigned char)0x03来摆脱那个字符,对吗?

2 个答案:

答案 0 :(得分:2)

使用continue时,会跳过字符0x03,但仍会执行j++,因此缓冲区会向前移动。

这意味着0x03实际上是未初始化的内存。

只需在循环结束时移动j++,而不是在循环声明中移动。

侧节点:阅读您的代码我得到的印象是它可以通过多种方式得到改进。也许你应该在错误修复后https://codereview.stackexchange.com/上询问它。

答案 1 :(得分:0)

如前所述,0x03是未初始化的内存。此外,您还有另一个问题:fseek(f1,ftell(f1),SEEK_SET)将文件位置移动到结尾。下一个fgetc()将返回EOF。因此,您的循环应如下所示:

for(i = ftell(f1)-1 ,j = 0; i&gt; = 0&amp;&amp; j&lt; = BS - 1; i - ,j ++){。 ...}