使用fgetc读取文件会产生额外的(垃圾)值

时间:2019-02-25 17:29:08

标签: c

我创建了一个从文本文件读取数据的功能。该函数将数据读入缓冲区,然后在缓冲区被填充时将其复制到单独的变量中。

我注意到 line_size (请参见下面的参考)变量超出了行的实际大小,即 line_size 的值为106,而我行的实际长度是103个字符。

为进行调试,我添加了一条打印语句,该语句将读取的每个字符与当前缓冲区大小相对应:printf("%c\t%i\n",c,current_buffer_size);

运行该程序后,结果发现 fgetc 正在读取一些“垃圾”字符(请参见下面的屏幕截图)。

(参考: char * line 存储来自缓冲区的数据, int line_size 跟踪char * line的大小)

注意FILE_BUFFER的值为128

enter image description here

char *readline(FILE *fptr)
{
  char buffer[FILE_BUFFER];
  char *line = malloc(sizeof(char));
  int current_buffer_size, line_size = 0;
  int c;
  int is_reading = 1;

  while(is_reading)
  {
    current_buffer_size = 0;
    while(current_buffer_size < FILE_BUFFER)
    {
      c = fgetc(fptr);
      if ( c == '\n' || feof(fptr))
      {
        is_reading = 0;
        break;
      }
      buffer[current_buffer_size] = c;
      current_buffer_size += 1;
      printf("%c\t%i\n",c,current_buffer_size);
    }
    line_size += current_buffer_size;
    line = (char *) realloc(line,line_size*sizeof(char));
    memcpy(&line[line_size-current_buffer_size], buffer, current_buffer_size);
  }
  if (line_size == 0) return NULL;
  line = (char *) realloc(line,(line_size+1)*sizeof(char));
  line[line_size] = 0;
  printf("\n%i\n",line_size); // final size of the line
  return line;
}

这可能是什么原因?

1 个答案:

答案 0 :(得分:1)

谢谢大家的有用评论。由于@JonathanLeffler和@dasblinkenlight

,该问题已得到解决。

因此,问题似乎出在文件中某些字符超出了单字节UTF-8范围(0-127)。由于我的文本编辑器和终端均以UTF-8模式运行,因此未显示这些字符。每个字符的二进制转储(使用xxd -b -c2 file.txt)揭示了此问题。 (完全公开:该文本文件是从whatsapp导出的。)

内存转储显示超出范围的字符(左)和“垃圾值”(右) enter image description here enter image description here

(三个字符:11100010 10000000 10001110引起了麻烦)

这还将解释由于字符的“额外计数”而导致应用程序抛出的其他看似莫名的内存错误。现在有很多道理。