【问题标题】:How to Detect Ctrl-z End of File Marker in C Programming Language如何在 C 编程语言中检测 Ctrl-z 文件结束标记
【发布时间】:2012-11-19 19:35:59
【问题描述】:

我正在尝试检测文件中的最后一个字节是否为 control-z (the MS-DOS originating end of file byte - 0x1A),但我没有成功。我正在使用

fseek(filePointer,-1,SEEK_END);

隔离最后一个字节,然后我正在使用

fread(buffer, sizeof(buffer[0]), sizeof(custom_char), filePointer);

尝试读取最后一个字节。

当我尝试读取该字节时,我基本上得到了垃圾,我想知道 fread 是否会默认忽略 0x1A 字节,或者是否存在人们过去在执行此操作时遇到的任何其他古怪行为。

当前出现故障的逻辑正在尝试读取最后一个字节并考虑如果 fread 返回 0 则找到文件末尾标记(fread 应该返回读取的元素数,对吗?):

if(fread(buffer, sizeof(buffer[0]), sizeof(custom_char), filePointer) == 0)
{
    // strip off the last byte
}

编辑: 我应该补充一点,我在调用 fopen 后出现的问题,BOM 被写入,并且 BOM 的第 3 个字节被错误地认为是文件标记的 0xA1 结尾并被剥离。

【问题讨论】:

  • 调用fopen时,是否将b(二进制)指定为mode参数的一部分?
  • @ChrisW 不。不过,我正在读写文本文件。使用 UTF-8 标志。
  • Ctrl+Z 是一个旧的 CP/M 约定,之所以需要,是因为它只能计算扇区,而不是字节。在 utf-8 编码文件中找到一个是一种恐龙和人类电影的时间不合时宜的现象。但是是的,当您以文本模式打开文件时,fread() 已经过滤了它。
  • 如果您使用的是 DOS/Windows,您应该在问题中提及这一点。在其他系统上,stdio 通常不会像那样处理您的数据。
  • @R.. 很抱歉。你是对的。我正在使用 DOS/Windows。

标签: c file-io fread


【解决方案1】:

您需要以二进制模式打开文件:

FILE *filePointer = fopen("yourfile.txt", "rb");

否则文件将以文本模式打开,这会将 CR-LF 字符对转换为 C '\n' 字符,并在 Windows/MSDOS 上摆脱 EOF 字符。

【讨论】:

  • 不幸的是,在我的代码中,我已经在确保模式是“a”或“a+”而不是二进制的条件语句中。我真的只是想抓住文件的最后一个字节(char)。
  • @Stubbs:然后您必须通过以二进制模式重新打开文件来作为单独的步骤进行检测。这是正确的答案。
  • @Adrian McCarthy 感谢您的帮助。
猜你喜欢
  • 2020-08-13
  • 1970-01-01
  • 2010-12-31
  • 1970-01-01
  • 1970-01-01
  • 2011-08-26
  • 1970-01-01
  • 2021-03-17
  • 2015-03-05
相关资源
最近更新 更多