pack('H*', dechex(12345678900)) /* on 32bit */ != pack('H*', dechex(12345678900)) /* on 64bit */
为什么?
最佳答案
我不知道如何解决它,但我想我知道为什么会这样。这里没有错误 - 直接从手册 http://php.net/manual/en/function.dechex.php
The largest number that can be converted is 4294967295 in decimal resulting to "ffffffff"
我不知道 php“内部”到底发生了什么,但您可能导致 32 位无符号整数溢出 (12,345,678,900 > 4,294,967,295)。因为在 64 位上这个限制应该是 18,446,744,073,709,551,615,dechex 返回“正确”值(似乎没有记录 32 位和 64 位差异,我可能是错的,因为我没有 64 位系统进行测试)。
//编辑:
作为最后的手段,您可以使用 GMP 扩展来为 32 位系统创建您自己的 hecdex 函数,但这会产生大量的开销。可能是现代编程已知的最慢的实现之一。
//编辑2:
使用 BCMath 编写了一个函数,我目前在 Windows 上并且正在努力为 GMP 寻找正确的 dll。
function dechex32($i) {
//Cast string
$i = (string)$i;
//Initialize result string
$r = NULL;
//Map hex values 0-9, a-f to array keys
$hex = array_merge(range(0, 9), range('a', 'f'));
//While input is lagrer than 0
while(bccomp($i, '0') > 0) {
//Modulo 16 and append hex char to result
$r.= $hex[$mod = bcmod($i, '16')];
//i = (i - mod) / 16
$i = bcdiv(bcsub($i, $mod), '16');
}
//Reverse result and return
return strrev($r);
}
var_dump(dechex32(12345678900));
/*string(9) "2dfdc1c34"*/
没有彻底测试,但似乎有效。作为最后的手段使用 - 100,000 次迭代的粗略基准测试确实表明,它比 native 实现慢约 40 倍。
关于php5 包在 x84_64 env 上损坏,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5799399/