2015-03-14 1 views
3

Мне нужно преобразовать большие числа в perl от десятичной до двоичной и наоборот.Perl десятичное и двоичное преобразование с большими числами

Пример номер этой длины:

Dec: 76982379919017706648824420266 
Bin: 111110001011111001010101000010011001000010101111001110000000000000000000000000000000000000000000 

В форумах я нашел две функции:

sub dec2bin { 
    my $str = unpack("B32", pack("N", shift)); 
    $str =~ s/^0+(?=\d)//; # otherwise you'll get leading zeros 
    return $str; 
} 
sub bin2dec { 
    return unpack("N", pack("B32", substr("0" x 32 . shift, -32))); 
} 

Но оба они, кажется, перестают работать, когда он получает такие большие числа .. .

Output of 
bin2dec(111110001011111001010101000010011001000010101111001110000000000000000000000000000000000000000000) 
is 1543163 
and output of 
dec2bin(76982379919017706422040262422) 
is 11111111111111111111111111111111 

Есть ли правильный способ сделать это с такими большими числами? Спасибо заранее!

ответ

3

Вы можете использовать Math::BigInt. Обратите внимание, что ввод этих функций должен быть строкой.

use Math::BigInt; 

sub bin2dec { 
    my $bin = shift; 
    return Math::BigInt->new("0b$bin"); 
} 

sub dec2bin { 
    my $dec = shift; 
    my $i = Math::BigInt->new($dec); 
    return substr($i->as_bin(), 2); 
} 

print "Dec: " . bin2dec("111110001011111001010101000010011001000010101111001110000000000000000000000000000000000000000000") . "\n"; 
print "Bin: " . dec2bin("76982379919017706648824420266") . "\n"; 

Выход: BIGINT

Dec: 76982379919017710405206147072 
Bin: 111110001011111001010101000010011001000010101111001101001001010101100110001100111001011110101010 
1

Perl обеспечивает built-in bignum facilities. Включите их с помощью use bignum;. Ваши функции преобразования будут выглядеть следующим образом:

use bignum; 
my ($b_orig, $d_orig, $b, $d); 

$d_orig = 76982379919017706648824420266; 
$b_orig = '111110001011111001010101000010011001000010101111001110000000000000000000000000000000000000000000'; 

print ("dec($b_orig) [orig] = $d_orig;\n"); 
print ("dec($b_orig) [comp] = " . Math::BigInt->from_bin($b_orig) . ";\n"); 
print ("bin($d_orig) [orig] = $b_orig;\n"); 
print ("bin($d_orig) [comp] = ".substr(Math::BigInt->new($d_orig)->as_bin(), 2).";\n"); 

Caveat

Там нет соответствия между двоичным и десятичным числом, которые вы предоставляете. Я не проверял, является ли это недостатком библиотеки bigint или нет.

1

Perl обеспечивает прозрачную поддержку для больших целых чисел:

perl -Mbigint -E 'say oct "0b111110001011111001010101000010011001000010101111001110000000000000000000000000000000000000000000"' 
76982379919017710405206147072

Вам не нужно написать собственную процедуру преобразования. oct будет конвертировать для вас.

Смежные вопросы