假设我有一个字符串5a
。
这是ASCII字母Z
的十六进制表示。
我需要找到一个Linux shell命令,它可以接收一个十六进制字符串并输出该字符串所代表的ASCII字符。
因此,如果我执行以下命令:
echo 5a | command_im_looking_for
我将会看到一个单独的字母Z
:
Z
我曾经使用 xxd 实现这个功能:
echo -n 5a | xxd -r -p
然后我意识到在Debian/Ubuntu中,xxd是vim-common的一部分,因此可能不存在于极简系统中。为了避免使用Perl(在我看来也不是最小系统的一部分),我最终使用sed、xargs和printf来实现此目的:
echo -n 5a | sed 's/\([0-9A-F]\{2\}\)/\\\\\\x\1/gI' | xargs printf
大多数情况下,我只想转换几个字节,对于这样的任务来说这是可以的。与ghostdog74的解决方案相比,这种解决方案的优势在于它可以自动地将任意长度的十六进制字符串转换为ASCII字符。使用xargs是因为printf不从标准输入读取。
echo -n 5a | perl -pe 's/([0-9a-f]{2})/chr hex $1/gie'
请注意,这不会跳过非十六进制字符。如果您只想获取十六进制(没有原始字符串中的任何空白等):echo 5a | perl -ne 's/([0-9a-f]{2})/print chr hex $1/gie'
此外,zsh
和bash
在echo
中本身就支持这个功能:
echo -e '\x5a'
perl -lne 'print pack "H*", $_'
更容易。 - Randal Schwartzecho -ne '\x5a'
是必需的。请注意,我已经尽力使翻译通俗易懂并保持了原意。 - antikecho -ne '\x5a\xde\x0b\x0d' | xxd
来测试是否一切正常。 - Giuseppe Crinò你可以仅使用echo
完成此操作,无需其他步骤。不要忘记添加 "-n",否则将自动换行:
echo -n -e "\x5a"
\x
。示例是5a
,但问题是将十六进制字符串转换为多个ASCII字符。 - Lorrinecho -n "5a" | while read -N2 code; do printf "\x$code"; done
echo -n "0102abcd" | while read -n 2 code; do printf "\x$code"; done | hexdump
输出0201 cdab
- John Steelecho -n "0102abcd" | while read -n 2 code; do printf "\x$code"; done | hexdump -e '/1 "%02x"'
- user3132194以下是适用于任何字节数的Python 3单行代码。
使用strip
,这样stdin上可以有换行符。
$ echo 666f6f0a | python3 -c "import sys, binascii; sys.stdout.buffer.write(binascii.unhexlify(input().strip()))"
foo
$ echo foo | python3 -c "import sys, binascii; print(binascii.hexlify(sys.stdin.buffer.read()).decode())"
666f6f0a
python3 -c 'import binascii; print(binascii.unhexlify(input()))' <<< 486921
- Matthias Braun根据你获得“5a”的方式,你可以在其前面添加“\x”,然后将其传递给printf
函数:
$ a=5a
$ a="\x${a}"
$ printf "$a"
Z
printf "\x${a}"
。 - Dennis Williamsonecho 5a | python -c "import sys; print chr(int(sys.stdin.read(),base=16))"
print
更改为 sys.stdout.write
可以防止额外的换行符字符。 - Brent BradburnOverflowError: Python int too large to convert to C long
- nmz787#warning : spaces do matter
die(){ echo "$@" >&2;exit 1;}
p=48656c6c6f0a
test $((${#p} & 1)) == 0 || die "length is odd"
p2=''; for ((i=0; i<${#p}; i+=2));do p2=$p2\\x${p:$i:2};done
printf "$p2"
for ((i=0; i<${#p}; i+=2));do p2+=\\x${p:$i:2};done
- starfrydc可以在不同的数字进制之间进行转换:
$ echo 5a | (echo 16i; tr 'a-z' 'A-Z'; echo P) | dc
Z$
有一个简单的 shell 命令 ascii
。
如果您使用 Ubuntu,请使用以下命令安装:
sudo apt install ascii
那么
ascii 0x5a
将输出:
ASCII 5/10 is decimal 090, hex 5a, octal 132, bits 01011010: prints as `Z'
Official name: Majuscule Z
Other names: Capital Z, Uppercase Z
"echo -n 5a | xxd -r -p"
,我更喜欢使用"xxd -r -p <<< 5a"
。好处: (1) 需要输入的字符更少(由于只需要键入3次,因此输入速度更快); (2) 只运行一个命令(省去了echo
),而不是两个 => 执行更快。 - Kurt Pfeiflesh: 1: Syntax error: redirection unexpected
缺点:不符合POSIX标准 - josch