如何在bash中将无符号十进制(小于1

如何在bash中将无符号十进制(小于1

例子:

$ decimal=$(( RANDOM << 17 | RANDOM << 2 | RANDOM >> 13 ))
$ echo $decimal
$ printf "%08x" $decimal | xxd -r -p >bytes

结果在bytes文件中。

是否可以在单个命令中完成,而无需先将其不必要地转换为十六进制?

答案1

您可以使用printf内置函数发出八进制代码给出的字节。

x=1193046
printf "$(printf "\\%03o" $((x>>24&255)) $((x>>16&255)) $((x>>8&255)) $((x&255)))"

答案2

您可以使用perl

$ perl -e 'print pack "I>", shift' $(( RANDOM << 17 | RANDOM << 2 | RANDOM >> 13 ))

答案3

dc可以采用任意输入基数并以同样任意的输出基数进行输出。您dc通过首先传递一个值来与之通信(或由空格分隔的值字符串)接下来是处理该值的命令。dc输入和输出默认都以 10 为基数。

例如,将任意十进制值转换为二进制值(或者至少以 2 为底):

printf 2o%dp "'A" | dc
1000001

这相当于以下命令列表dc

  1. 将 2 添加到主堆栈顶部

  2. 从主堆栈中弹出顶部值并将其值用作o输出基数

  3. 添加 65(在我的区域设置中转换的 A 的 ASCII 十进制值printf到主堆栈的顶部

  4. 从主堆栈中弹出顶部值并将p其值打印到stdout当前指定为输出基数的基数中

dc还将打印由其输入基数解释的字节的 ASCII 值:

printf 8i%oP "'A" | dc
A

...和...

printf 2i%sP 1000001 | dc
A

该过程与之前的过程非常相似,除了i用于指定i输入基数(而不是之前的o输出基数)以及P用于将顶部堆栈值解释为输出上的 ASCII 字符之外。

bc可以做很多相同的事情,尽管它的语法往往更加冗长。做man dc更多man bc。不过,按位移位并不属于这两个程序的功能。尽管如此,正如您所展示的,任何 POSIX shell 都可以相当轻松地通过算术扩展来处理这一问题。

相关内容