【问题标题】:Determine whether a file contains binary or ASCII data确定文件是否包含二进制或 ASCII 数据
【发布时间】:2010-11-05 02:09:25
【问题描述】:

我将文件作为输入参数,我需要确定数据是否为二进制(我猜是 ASCII 或二进制),类似于 *nix 上的“文件”命令,但在我的应用程序中.

我不知道该怎么做,因为当我读取数据时,我就是这样做的:

fread(&rndByte, sizeof(unsigned int), 1, fp);
// reading one unsigned int at a time from file fp

我正在考虑多次测试该值是否

有什么想法、建议吗?

【问题讨论】:

  • 如果您的文本中有任何特殊字符,您的检查将会失败。此外,逐字节读取非常慢。
  • 你为什么一次读unsigned int?一次阅读char 会容易得多。
  • 您究竟为什么需要这样做?
  • 这是一个家庭作业,我们需要读取一个无符号整数,然后对其进行算术运算以确定程序如何进行。可悲的是,我无法更改正在读取的数据量,因为这是必需的。但是,我想一个 char 可能会工作......但我认为将它保留为 unsigned int 会更容易。
  • 您正在寻找满足家庭作业(愚蠢)要求的算术是按位和运算符。假设你的 unsigned int 是 32 位,if (x & 0x80808080) 将同时测试 4 个字节的高位。

标签: c file-io ascii binary-data file-type


【解决方案1】:

我正在考虑测试该值是否

认为文本(即使是英语)永远不会包含基本拉丁语以外的字符是天真的想法。 Microsoft® 程序尤其喜欢在文本中添加破折号和“智能引号”。

更好的方法是查找 ASCII 控制字符。文本文件往往会有很多换行符(\n 和/或\r,具体取决于平台),可能还有一些制表符,但几乎没有任何其他控制字符。

【讨论】:

  • 我期望的输入(如果是 ascii)可能只包含该范围内的几个基本字符。但是 \n 字符是一个很好的建议,谢谢。
【解决方案2】:

正如其他人所说(尽管不那么直截了当),在 2010 年将文本限制为 ASCII 是完全倒退的。由于非文本二进制数据解析为 UTF-8 的概率极低,一个更好的方法是尝试解析整个文件为 UTF-8,并在第一次失败时将其声明为二进制。

正如其他人所说,与其在小单元上一遍又一遍地调用freadfgetc,不如将​​fread 一次大块(1-4k)放入固定大小的缓冲区并运行你的解析器,每当你到达终点时读取一个新的块。 (如果您的 UTF-8 解析器不容易重新启动,则将缓冲区的末尾memcpy 重新填充到缓冲区的开头并在缓冲区中剩余少于 4 个字节时重新填充可能是有意义的。)

【讨论】:

    【解决方案3】:

    使用fread() 获取整个 1024 字节(或 512 或任何适合您的)缓冲区,然后逐字节扫描该缓冲区以查找设置了第八位的内容。这可能与 file(1) 所做的非常接近,只是 file(1) 需要考虑更复杂的模式,而且它可能不会为这么大的缓冲区而烦恼。

    您还可以获取find 的源代码并了解其运作方式。

    【讨论】:

      猜你喜欢
      • 2012-08-26
      • 2021-11-04
      • 2015-04-24
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2010-10-22
      • 2016-05-03
      • 1970-01-01
      相关资源
      最近更新 更多