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

新手上路,请多包涵

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

我试过看 printf 和谷歌,但我什么也找不到。

非常感谢任何帮助。

提前谢谢了,

原文由 Eamorr 发布,翻译遵循 CC BY-SA 4.0 许可协议

阅读 1.8k
2 个回答
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 个字节。

原文由 Tomas 发布,翻译遵循 CC BY-SA 4.0 许可协议

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

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

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

  • sed 一个流式 编辑 器。
  • s 替代命令。
  • / 打开正则表达式 - 可以使用任何字符。 / 是常规的,但对于处理 XML 或路径名等不方便。
  • / 或您选择的替代字符,关闭正则表达式并打开替换字符串。
  • / */ 中, * 匹配前一个字符的任何序列(在本例中为空格)。
  • / 或您选择的替代字符,关闭替换字符串。在这种情况下,替换字符串 // 为空,即匹配被删除。
  • g 在每一行进行全局替换的选项,而不是每行一次。
  • 引号使命令解析器不会混淆 - 整个序列被传递给 sed 作为第一个选项,即 sed 脚本。

@TMS 脑子( sed 's/^ *//' )只从每行的开头删除空格( ^ 匹配行的开头 - sed f3e2a883e42af2070371e42cd85a51c 中的“模式空间”说话)。

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

| tr -d '\n'

到命令管道。它的作用如下:

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

sed 在处理换行符时具有独特的延迟。这是因为 sed 是最古老的 unix 命令之一 - 它是在人们真正知道自己在做什么之前创建的。无处不在的遗留软件使其无法修复。我知道这一点,因为我在 unix 出生之前出生。

问题的历史起源是换行符是行分隔符,而不是行的一部分。因此,它被行处理实用程序剥离并由输出实用程序重新插入。问题是,这对用户数据的结构做出了假设,并在许多环境中施加了不自然的限制。 sed 无法轻松删除换行符是导致悲伤的畸形意识形态最常见的例子之一。

可以使用 sed 删除换行符 - 只是我所知道的所有解决方案 make sed 一次处理整个文件,这会阻塞非常大的文件,违背了流编辑器。如果可能的话,任何保留线处理的解决方案都将是一个不可读的多个管道的老鼠窝。

如果你坚持使用 sed 试试:

 sed -z 's/\n//g'

-z 告诉 sed 使用空值作为行分隔符。

在内部, C 中的字符串以空值结尾。 -z 选项也是遗留的结果,为 C C 程序员提供便利通过换行符。然后他们可以轻松地一次读取和处理一个字符串。同样,关于用例的早期假设对用户数据施加了人为的限制。

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

你可能认为

sed 's/^/\x00/' | sed -z 's/\n//' | sed 's/\x00//'

可能会奏效。第一个命令逐行在每行的前面放置一个空值,导致 \n\x00 结束每一行。第二个命令从每行中删除一个换行符,现在由空值分隔 - 由于第一个命令,将只有一个换行符。剩下的就是虚假的空值。到目前为止,一切都很好。这里的错误想法是管道将逐行提供最后一个命令,因为这就是构建流的方式。实际上,所写的最后一个命令只会删除一个空值,因为现在整个文件没有换行符,因此是一行。

简单的管道实现使用一个中间临时文件,所有输入都被处理并馈送到文件中。下一个命令可能在另一个线程中运行,同时读取该文件,但它只是将流视为一个整体(尽管不完整)并且不知道馈送文件的块边界。即使管道是内存缓冲区,下一个命令也会将流视为一个整体。该缺陷与 sed 密不可分。

为了使这种方法有效,您需要在最后一个命令上添加一个 g 选项,因此,它再次阻塞了大文件。

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

原文由 I_always_RTFM_and_STFW 发布,翻译遵循 CC BY-SA 4.0 许可协议

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题