如何将十六进制的unsigned char数组打印到文件中?

时间:2017-08-04 01:21:53

标签: c arrays hex printf

我实际上尝试在文件的十六进制表示中fprintf unsigned char数组。

为此,我使用此代码:

#include <stdio.h>
#include <stdlib.h>

int main()
{
    unsigned char tab[...] = "...";

    FILE* Output = NULL;
    Output = fopen("Output.txt", "w+");

    tabLength = sizeof(tab);
    for ( unsigned int i = 0; i < tabLength; i++ )
        fprintf(Output, "%2X", tab[i]);

    fclose(Output);
}

使用小数组,没有问题,但因为它倾向于大数组(在我的情况下是200M元素),它会变得更长:(

如果你们中的一些人有选择以更快的方式完成工作,我会很高兴:)

编辑: tabLength = strlen(tab) - &gt; tabLength = sizeof(tab);

2 个答案:

答案 0 :(得分:3)

有关将十六进制缓冲区转储到文件中的更快方法,请使用基于手工编码块的方法:

  • 没有fprintf()开销
  • 更少的库函数调用,相应地减少锁定。
  • 以4K的块(或更高的2的幂)写入以支持页面对齐,从而有机会fwrite绕过缓冲阶段。

以下是代码:

#define CHUNK 2048

void dumphex(const unsigned char *a, size_t size, FILE *fp) {
    char buf[CHUNK * 2];
    const char *xdigits = "0123456789ABCDEF";
    size_t i, j;

    for (; size >= CHUNK; size -= CHUNK, a += CHUNK) {
        for (i = j = 0; i < CHUNK; i++, j += 2) {
            unsigned char c = a[i];
            buf[j + 0] = xdigits[c >> 4];
            buf[j + 1] = xdigits[c & 15];
        }
        fwrite(buf, 2, CHUNK, fp);
    }
    for (i = j = 0; i < size; i++, j += 2) {
        unsigned char c = a[i];
        buf[j + 0] = xdigits[c >> 4];
        buf[j + 1] = xdigits[c & 15];
    }
    fwrite(buf, 2, size, fp);
}

答案 1 :(得分:2)

代码使用tab调用和strlen()循环运行for两倍的长度。

tabLength = strlen(tab); // waste
for ( unsigned int i = 0; i < tabLength; i++ )
    fprintf(Output, "%2X", tab[i]);

相反只运行一次长度。

for ( unsigned int i = 0; tab[i]; i++ )
    fprintf(Output, "%2X", tab[i]);

此外,我认为OP的前提是形成不良的。使用tabLength = strlen(tab);查找长度意味着unsigned char array字符串。相反,我怀疑unsigned char array的真实长度可以通过其他方式找到。

通常情况下,重复调用fprintf()以打印2个字符最好在16,64,4096等组中完成。在这种情况下,@DYZ有好主意。以块的形式打印到本地缓冲区,然后打印缓冲区。

for (unsigned int i = 0; i < tabLength; i++ )
    fprintf(Output, "%2X", tab[i]);

轻微:更典型的共振峰是"%02X"。这取决于您是否需要前导空格或0是否值小于16。