【问题标题】:Convert hex stream to GIF将十六进制流转换为 GIF
【发布时间】:2011-10-09 13:19:37
【问题描述】:

如何从以下 HEX 流创​​建 .gif 文件:

0d 0a 0d 0a 47 49 46 38 39 61 01 00 01 00 80 ff 00 ff ff ff 00 00 00 2c 00 00 00 00 01 00 01 00 00 02 02 44 01 00 3b

3b 是 GIF 文件的终止符

我正在尝试按照http://en.wikipedia.org/wiki/Graphics_Interchange_Format#Example_GIF_file 的指南进行操作

我想在 Perl 或 C/C++ 中实现它。不过任何语言都可以。

非常感谢,


感谢大家的回复。我删除了领先的 '0d 0a 0d 0a'...

这是我目前所拥有的:

#!/usr/bin/perl
use strict;
use warnings;

open(IN,"<test.txt");
open(OUT,">test.gif");

my @lines=<IN>;

foreach my $line (@lines){
        $line=~s/\n//g;
        my @bytes=split(/ /,$line);
        foreach my $byte (@bytes){
                print OUT $byte;
        }
}
close(OUT);
close(IN);

【问题讨论】:

  • 嗯,您将字节写入文件?抱歉,我没发现问题,可能是因为您没有真正提出问题。
  • 应该如何将十六进制流转换为 GIF?最简单的解决方案似乎是将其输入 MS Paint 并将其保存为 .gif :P
  • 用您感兴趣的任何语言查找“文件 I/O”。打开文件,写入字节,关闭文件。完成。
  • 只需在 C 或 C++ 中插入 chr(i) foreach my $i (@image); 即可。
  • 顺便说一句...您可能想跳过前导 0d 0a 0d 0a

标签: c++ c perl hex gif


【解决方案1】:

您可以在 shell 中使用GNU echo

$ /bin/echo -n -e "\x47\x49\x46\x38\x39\x61\x01\x00\x01\x00\x80\xff\x00\xff\xff\xff\x00\x00\x00\x2c\x00\x00\x00\x00\x01\x00\x01\x00\x00\x02\x02\x44\x01\x00\x3b" > foo.gif

$ identify foo.gif
foo.gif GIF 1x1 1x1+0+0 8-bit PseudoClass 2c 36B 0.000u 0:00.000

您还可以使用xxd 命令“进行十六进制转储或执行相反操作”。然而,令人讨厌的是,它似乎对输入格式非常挑剔。这是一个使用xxd的例子:

$ cat > mygif.hex <<END
0000000: 4749 4638 3961 0100 0100 80ff 00ff ffff
0000010: 0000 002c 0000 0000 0100 0100 0002 0244
0000020: 0100 3b0a
END

$ xxd -r < mygif.hex > mygif.gif

gvim 有一个到xxd 的接口。使用“工具→转换为十六进制”菜单选项(键盘::%!xxd),然后使用“工具→转换回”(:%!xxd -r)。

EMACS 还有一个内置的十六进制编辑器,可以通过M-x hexl-mode 访问(参见手册中的Editing Binary Files)。这也有点烦人,因为您必须在通过十六进制代码输入字符之前输入C-M-x(即Ctrl-Meta-X):

当然,写一个简单的C程序来做转换是很容易的:

#include <stdio.h>

int main(int argc, char **argv) {
  unsigned int c;
  while (1 == scanf("%x", &c))
    putchar(c);
  return 0;
}

用法:

$ gcc -Wall unhexify.c -o unhexify
$ echo  "47 49 46 38 39 61 01 00 01 00 80 ff 
         00 ff ff ff 00 00 00 2c 00 00 00 00 
         01 00 01 00 00 02 02 44 01 00 3b" | ./unhexify > mygif.gif

还有:many answers here in this code golf question

【讨论】:

  • +1 我不知道 Emacs 具有十六进制模式功能。感谢您展示它。
【解决方案2】:
perl -ne'
   BEGIN { binmode STDOUT }
   s/\s//g;
   print pack "H*", $_;
' file.hex > file.gif

Perl 5.14:

perl -ne'
   BEGIN { binmode STDOUT }
   print pack "H*", s/\s//gr;
' file.hex > file.gif

(如果您想打高尔夫球,可以将-nprint替换为-p$_ =(缩短程序的长度。)

【讨论】:

    【解决方案3】:
    • 使用.gif 扩展名打开一个新文件进行写入(以二进制模式)。
    • 读取每对十六进制字符。
    • 将十六进制转换为字节 (char) 值。
    • 将字节写入打开的文件。
    • 完成后,关闭文件。

    如果十六进制数据代表 GIF 图像,文件应该包含它。

    【讨论】:

      【解决方案4】:

      您可能需要阅读unpack(或hex)和pack 的文档。您可能还会发现 perlio 文档对于创建原始文件句柄很有用(因此 perl 不会尝试帮助您处理编码或行尾等问题)。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2011-07-28
        • 1970-01-01
        • 1970-01-01
        • 2017-07-31
        • 2015-11-11
        相关资源
        最近更新 更多