在命令行上将字符串转换为十六进制

时间:2011-07-22 14:50:40

标签: linux string command-line hex printf

我正在尝试使用命令行尽可能高效地将“Hello”转换为十六进制的48 65 6c 6c 6f

我试过看printf和谷歌,但我无法到达任何地方。

非常感谢任何帮助。

非常感谢,

5 个答案:

答案 0 :(得分:43)

echo -n "Hello" | od -A n -t x1

说明:

  • echo程序将字符串提供给下一个命令。
  • -n标志告诉echo在“Hello”结尾处不生成新行。
  • od程序是“八进制转储”程序。 (我们将提供一个标志,告诉它以十六进制而不是八进制转储它。)
  • -A n标志是--address-radix=n的缩写,n是“none”的缩写。如果没有此部分,该命令将在左侧输出一个丑陋的数字地址前缀。这对于大型转储非常有用,但对于短字符串则没有必要。
  • -t x1标志是--format=x1的缩写,x表示“十六进制”,1表示1字节。

答案 1 :(得分:4)

显然,@ TM无法进行RTFM。 (见他对以前回答的评论)

如果你想这样做并删除你需要的空格:

echo -n "Hello" | od -A n -t x1 | sed 's/ *//g'

@TMS在他的回答中很好地解释了管道中的前两个命令,由@James编辑。最后一个命令与@TMS注释的不同之处在于它是正确的并且已经过测试。解释是:

  • sed s tream ed itor。
  • s s ubstitute命令。
  • /打开正则表达式 - 可以使用任何字符。 /是    传统的,但不便于处理,比如XML或路径名。
  • /或您选择的替代字符,关闭正则表达式和    打开替换字符串。
  • / */ *匹配前一个字符的任何序列(在此处 case,a space)。
  • /或您选择的替代字符会关闭替换字符串。    在这种情况下,替换字符串//为空,即匹配为    删除。
  • g可以选择在每行上替换 g    每行只有一次。
  • 引号使命令解析器不会混淆 - 整体 序列作为第一个选项传递给sed,即sed脚本。

@TMS脑儿(sed 's/^ *//')仅从每行开头删除空格(^匹配行的开头 - &{39;模式空间' {{1} } -speak)。

如果您还想删除换行符,最简单的方法是追加

sed

到命令管道。它的功能如下:

  • | tr -d '\n' 将先前处理的流提供给此命令的标准输入。
  • | tr anslate命令。
  • tr指定删除匹配字符。
  • 引号列出您的匹配字符 - 在这种情况下只是换行符(-d)。 翻译仅匹配单个字符,而不是序列。
在处理换行符时,

\n是唯一的延迟。这是因为sed是最古老的sed命令之一 - 它是在人们真正知道他们在做什么之前创建的。普及的传统软件使其无法修复。我知道这是因为我出生在unix出生之前。

问题的历史根源是换行是一个行分隔符,而不是行的一部分。因此它被线处理实用程序剥离并由输出实用程序重新插入。麻烦的是,这会假设用户数据的结构,并在许多设置中施加不自然的限制。 unix无法轻易删除换行符是导致悲伤的格式错误的意识形态最常见的例子之一。

可以使用sed删除换行符 - 只是我知道的所有解决方案make sed一次处理整个文件,这会阻塞非常大的文件,从而无法实现流编辑器。任何保留线处理的解决方案,如果可能的话,将是一个难以理解的老鼠的多个管道的巢。

如果您坚持使用sed,请尝试:

sed

sed -z 's/\n//g' 告诉-z使用空值作为行分隔符。

在内部,sed中的字符串以null结尾。 C选项也是遗留的结果,为-z程序员提供便利,他们可能希望使用填充了C字符串的临时文件,并使用换行符整理。然后,他们可以轻松地一次读取和处理一个字符串。同样,关于用例的早期假设对用户数据施加了人为限制。

如果省略C选项,则此命令仅删除第一个换行符。使用g选项-z将整个文件解释为一行(除非文件中嵌入了杂散空值),以null结尾,因此这也会对大文件造成阻塞。

你可能会想到

sed

可能会奏效。第一个命令在每行的前面逐行放置一个null,从而导致sed 's/^/\x00/' | sed -z 's/\n//' | sed 's/\x00//' 每行结束。第二个命令从每一行中删除一个换行符,现在由空值分隔 - 根据第一个命令只有一个换行符。剩下的只是假的空值。到现在为止还挺好。这里破碎的想法是管道将逐行提供最后一个命令,因为这是流的构建方式。实际上,写的最后一个命令只会删除一个null,因为现在整个文件没有换行符,因此只有一行。

简单管道实现使用中间临时文件,并处理所有输入并将其提供给文件。下一个命令可能正在另一个线程中运行,同时读取该文件,但它只是将流视为一个整体(虽然不完整),并且不知道提供文件的块边界。即使管道是内存缓冲区,下一个命令也会将流视为一个整体。这个缺陷不可分割地融入\n\x00

要使此方法有效,您需要在最后一个命令上使用sed选项,因此它会在大文件上发生阻塞。

底线是:不要使用g来处理换行。

答案 2 :(得分:2)

echo hello | hexdump -v -e '/1 "%02X "'

答案 3 :(得分:1)

进一步解决这个问题, 一个工作的解决方案是删除“*”,如果需要替换实际字符,原始要求也不必简单地删除空格,如下所示

echo -n "Hello" | od -A n -t x1 | sed 's/ /%/g'

%48%65%6c%6c%6f

因此,我认为这是对原始问题的一种改进,因为声明现在完全符合要求,而不仅仅是显而易见。

答案 4 :(得分:0)

结合了TMS和i-always-rtfm-and-stfw的答案,以下在Windows下使用程序'od','sed'和'tr'的gnu-utils版本在Windows下工作:

echo "Hello"| tr -d '\42' | tr -d '\n' | tr -d '\r' | od -A n -tx1 | sed "s/ //g"

或在CMD文件中为:

@echo "%1"| tr -d '\42' | tr -d '\n' | tr -d '\r' | od -A n -tx1 | sed "s/ //g"

我的解决方案有一个限制,那就是它将删除所有双引号(“)。

"tr -d '\42'" removes quote marks that the Windows 'echo' will include.
"tr -d '\r'" removes the carriage return, which Windows includes as well as '\n'.
The pipe (|) character must follow immediately after the string or the Windows echo will add that space after the string.
There is no '-n' switch to the Windows echo command.