Perl - 将十六进制转换为二进制并将其用作字符串

问题描述 投票:5回答:4

我是Perl的新手,我在使用不同类型时遇到了困难。

我试图获得一个十六进制寄存器,将其转换为二进制,使用它一个字符串,并从二进制字符串中获取子串。

我做了一些搜索,我尝试的是:

my $hex = 0xFA1F;
print "$hex\n";

结果是“64031”。第一个惊喜:我不能在Perl中打印十六进制值而不仅仅是十进制值?

$hex = hex($hex);
print "$hex\n";

结果是409649.第二个惊喜:我希望结果也是64031,因为“hex”将十六进制转换为十进制。

my $bin = printf("%b", $hex);

它打印二进制值。有没有办法将十六进制转换为bin而不打印它?

谢谢,SLP

perl type-conversion hex bin
4个回答
4
投票

十进制,二进制和十六进制是数字的所有文本表示(即写入数字的方式)。计算机不能将这些作为数字来处理。

my $num = 0xFA1F;将指定的数字(六万四千三十一)存入$num。它以硬件理解的格式存储,但这不是很重要。重要的是它存储为数字,而不是文本。

print被要求打印一个数字时,它会以十进制打印出来(或者如果大/小就用科学记数法打印出来)。它不知道如何创建(从一个十六进制常量?来自添加?等),所以它无法确定如何根据它输出数字。

要将数字打印为十六进制,您可以使用

my $hex = 'FA1F';   # $hex contains the hex representation of the number.
print $hex;         # Prints the hex representation of the number.

要么

my $num = 0xFA1F;   # $num contains the number.
printf "%X", $num;  # Prints the hex representation of the number.

3
投票

您正在使用十六进制格式分配整数值。 print默认以十进制格式打印数字,因此您获得的是64031。

您可以使用printf()通过提供不同的格式来验证这一点。

$ perl -e ' my $num = 0xFA1F; printf("%d %X %b\n", ($num) x 3 ) '
64031 FA1F 1111101000011111

$ perl -e ' my $num = 64031; printf("%d %X %b\n", ($num) x 3 ) '
64031 FA1F 1111101000011111

$ perl -e ' my $num = 0b1111101000011111; printf("%d %X %b\n", ($num) x 3 ) '
64031 FA1F 1111101000011111

$

要在字符串中获取0xFA1F的二进制格式,可以使用sprintf()

$ perl -e ' my $hex = 0xFA1F; my $bin=sprintf("%b",$hex) ; print "$bin\n" '
1111101000011111

$

2
投票

让我们按顺序解决每一点困惑

my $hex = 0xFA1F;

这在$hex中存储了一个十六进制常量,但是Perl没有十六进制数据类型,所以尽管你可以编写十六进制常量,以及二进制和八进制常量,Perl将它们全部转换为十进制。请注意,两者之间存在很大差异

my $hex = 0xFA1F;

my $hex = '0xFA1F';

第一个将一个数字存储到$ he​​x中,当你打印出来时你得到一个十进制数字,第二个存储一个字符串,当打印出来时会给出0xFAF1但是可以传递给hex()函数转换为十进制。

$hex = hex($hex);

十六进制函数将字符串转换为十六进制数并返回十进制值,并且到目前为止,$hex只被用作数字Perl首先将字符串化$hex然后将字符串传递给hex()函数进行转换该值从十六进制到十进制。

所以对解决方案。你几乎在那里使用printf(),有一个名为sprintf()的函数,它采用与printf()相同的参数,但不是打印格式化的值,而是将其作为字符串返回。所以你需要的是。

my $hex = 0xFA1F;
my $bin = sprintf("%b", $hex);
print $bin;

技术说明:是的我知道Perl在内部将所有数字都存储为二进制数,但是不能去那里寻求答案,好吗?


2
投票

如果你可以使用发行版,我写了Bit::Manip来使我的原型设计在处理寄存器时更容易一些(如果你在编译XS代码时遇到问题,还有一个Pure Perl版本可用)。

它不仅可以从数字中取出位,还可以切换,清除,设置等:

use warnings;
use strict;

use Bit::Manip qw(:all);

my $register = 0xFA1F;

# fetch the bits from register using msb, lsb

my $msbyte = bit_get($register, 15, 8);

print "value: $msbyte\n";

print "bin: " . bit_bin($msbyte) . "\n";

# or simply:
# printf "bin: %b\n", $msbyte;

输出:

value: 250
bin: 11111010

这是我写的blog post,它展示了如何使用一些软件的功能和示例数据表寄存器。

© www.soinside.com 2019 - 2024. All rights reserved.