尝试使用 printf 解码作为参数传入的 unicode 字符

Ale*_*502 3 bash unicode printf

我正在尝试打印一些像这样输入的 unicode 代码

echo 0024 0025 | xargs -n1 echo # one code per line
  | xargs printf '\u%s\n'
Run Code Online (Sandbox Code Playgroud)

希望得到这个

$
%
Run Code Online (Sandbox Code Playgroud)

但这就是我得到的

printf: missing hexadecimal number in escape
Run Code Online (Sandbox Code Playgroud)

经过一些试验和错误,我实际上有两个较小的问题,一种是有道理的,另一种似乎完全是个谜。


问题1:

echo 0024 0025 | xargs -n1 echo # one code per line
  | xargs printf '\u%s\n'
Run Code Online (Sandbox Code Playgroud)

给我这个

-bash: printf: missing unicode digit for \u
\u0024
-bash: printf: missing unicode digit for \u
\u0025
Run Code Online (Sandbox Code Playgroud)

问题2:

$
%
Run Code Online (Sandbox Code Playgroud)

(使用>for$以便您可以$在输出中看到)

出于某种原因,有些字符适用于 exe 版本,但有些字符即使使用内置 printf 也适用。


所以这里有一个解决方法,如果不是问题#2,它会起作用(但可能比我原来的想法慢很多)

echo 0024 0025 | xargs -n1 echo # one item per line
  | xargs -I {} printf '\u{}\n'
Run Code Online (Sandbox Code Playgroud)

但由于问题 #2,它有点工作:

$ echo 0024 0025 | xargs -n1 echo | xargs -I {} printf '\u{}\n'
$
printf: invalid universal character name \u0025
Run Code Online (Sandbox Code Playgroud)

($ 出来但 % 出错)


所以我想我的问题是:

- 有没有办法让 printf 与数字代码一起工作,以便我可以运行 printf 一次而不是每个参数一次-I

-我做错了什么,printf内置不介意,但printfexe 不喜欢,但只为%而不是为$

Ste*_*itt 7

为了避免双展开问题(\u之前处理过%s),你可以使用%b,至少在 Bash 中printf

printf '%b\n' \\u0024 \\u0025
Run Code Online (Sandbox Code Playgroud)

您可以通过多种方式预处理您的输入:

set 0024 0025
printf '%b\n' "${@/#/\\u}"
Run Code Online (Sandbox Code Playgroud)

独立printf如GNU的coreutils实现,对Unicode字符规格以下限制:

printf解释 ISO C 99 中引入的两种字符语法: ' \u' 表示 16 位 Unicode (ISO/IEC 10646) 字符,指定为四个十六进制数字hhhh,以及 ' \U' 表示 32 位 Unicode 字符,指定为八个十六进制数字hhhhhhhhprintf根据LC_CTYPE语言环境输出 Unicode 字符。此语法不能指定 U+0000…U+009F、U+D800…U+DFFF 范围内的 Unicode 字符,但 U+0024 ($)、U+0040 (@) 和 U+0060 (`) 除外.

这就解释了为什么你不能%以这种方式生产。