首页 > 解决方案 > 使用 fgetc 读取文件会提供额外的(垃圾)值

问题描述

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

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

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

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

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

:值为FILE_BUFFER128

在此处输入图像描述

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;
}

这可能是什么原因?

标签: c

解决方案


谢谢大家的有用意见。感谢@JonathanLeffler 和@dasblinkenlight,问题已得到解决

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

内存转储显示超出范围的字符(左)和“垃圾值”(右) 在此处输入图像描述 在此处输入图像描述

(三个字:11100010 10000000 10001110闹事)

这也可以解释应用程序由于字符的“额外计数”而引发的其他看似莫名其妙的内存错误。现在很多事情都说得通了。


推荐阅读