使用PHP hexdec的大十六进制值

使用PHP hexdec的大十六进制值,php,hex,Php,Hex,我有一些大的十六进制值,我想显示为正则数,我使用hexdec()转换为float,我在PHP.net上找到了一个函数将其转换为十进制,但它似乎达到了上限,例如: $h = 'D5CE3E462533364B'; $f = hexdec($h); echo $f .' = '. Exp_to_dec($f); 输出:1.5406319846274E+19=154063198462740000 calc.exe的结果=15406319846273791563 还有其他方法可以转换大的十六进制值吗?

我有一些大的十六进制值,我想显示为正则数,我使用hexdec()转换为float,我在PHP.net上找到了一个函数将其转换为十进制,但它似乎达到了上限,例如:

$h = 'D5CE3E462533364B';
$f = hexdec($h);
echo $f .' = '. Exp_to_dec($f);
输出:1.5406319846274E+19=154063198462740000

calc.exe的结果=15406319846273791563

还有其他方法可以转换大的十六进制值吗?

intval(var,base)不会处理它吗

从上所述的。

该函数现在可以转换值 这对平台来说太大了 整数类型,它将返回值 在这种情况下,则改为浮动

如果您想要获得某种大整数(不是浮点),则需要将其存储在字符串中。这可能是使用函数实现的

例如,如果您查看hexdec手册页面的注释,您会发现

如果您稍微调整该功能,以避免出现通知,您将得到:

function bchexdec($hex)
{
    $dec = 0;
    $len = strlen($hex);
    for ($i = 1; $i <= $len; $i++) {
        $dec = bcadd($dec, bcmul(strval(hexdec($hex[$i - 1])), bcpow('16', strval($len - $i))));
    }
    return $dec;
}
输出将是:

string '15406319846273791563' (length=20)
所以,不是你所拥有的那种大浮动;并且似乎符合您的期望:

来自calc.exe的结果= 15406319846273791563


希望这有帮助;-)

是的,PHP文档中的用户注释有时是一座真正的金矿;-)

1.5406319846274E+19是您号码的有限表示。通过使用printf()可以得到一个更完整的

…将输出“15406319846273792000”。PHP对如此大的数字使用浮点数,因此可能会丢失一点精度。如果必须使用任意精度的数字,可以尝试以下方法。通过将十六进制拆分为两个32位字(在大多数系统中应该是安全的),您应该能够获得更高的精度。例如:

$f = bcadd(bcmul(hexdec(substr($h, 0, -8)), 0x100000000), hexdec(substr($h, 8)));
…将$f设置为15406319846273791563。

当结果太大而无法表示为int时,hexdec()将从int切换为float。如果您想要任意长的值,您可能需要使用自己的转换函数将十六进制字符串更改为

这就是要使用的模块。将其转换为函数,然后在数字上使用

注意:将这些十六进制数作为字符串提供,以便:

$num = "0x348726837469972346"; // set variable
$gmpnum = gmp_init("$num"); // gmp number format
echo gmp_strval($gmpnum, 10); // convert to decimal and print out

将十六进制转换为十进制很容易。。但是,重构十六进制数是非常困难的。 试着用


在MySQL数据库中存储64位密钥时遇到此问题。我能够使用一些二进制运算符将位完美转换为64位有符号整数(PHP限制):(此代码比bchexdec函数快16倍,生成的变量平均占用一半内存)

功能x64toSignedInt($k){
$left=hexdec(substr($k,0,8));
$right=hexdec(substr($k,8,8));

return(int)($left var_dump(intval('D5CE3E462533364B',16));得到的是int 2147483647;不是他所期望的^^;请参阅intval文档上的注释,其中指出:“最大值取决于系统。32位系统的最大有符号整数范围为-2147483648到2147483647。例如,在这样的系统上,intval('1000000000000')将返回2147483647。“我本来会将此设置为答案,但我没有安装GMP扩展(尽管可能我应该安装)。非常感谢。我已经安装了BC Math,因此这得到了GMP解决方案的‘答案’,但我确信两者都能完成此工作。谢谢:)至少在我的测试中,我猜base_convert仍在将其转换为float。如果运行base_convert(“9bdb999850d41000”,16,10),您将得到11230738975248618662,而真正的答案应该是11230738975248617472。请注意这一点。这只适用于16个字符的十六进制。任何更短的字符都会给出错误的结果
$f = bcadd(bcmul(hexdec(substr($h, 0, -8)), 0x100000000), hexdec(substr($h, 8)));
function gmp_hexdec($n) {
  $gmp = gmp_init(0);
  $mult = gmp_init(1);
  for ($i=strlen($n)-1;$i>=0;$i--,$mult=gmp_mul($mult, 16)) {
    $gmp = gmp_add($gmp, gmp_mul($mult, hexdec($n[$i])));
  }
  return $gmp;
}

print gmp_strval(gmp_hexdec("D5CE3E462533364B"));

Output: 15406319846273791563
$num = gmp_init( '0xD5CE3E462533364B' ); // way to input a number in gmp
echo gmp_strval($num, 10); // display value in decimal
$num = "0x348726837469972346"; // set variable
$gmpnum = gmp_init("$num"); // gmp number format
echo gmp_strval($gmpnum, 10); // convert to decimal and print out
$hexadecimal = base_convert(2826896153644826, 10, 16);
// result: a0b0c0d0e0f1a
function x64toSignedInt($k){
    $left = hexdec(substr($k,0,8));
    $right = hexdec(substr($k,8,8));
    return (int) ($left << 32) | $right;
}