在PHP(比特币)中读取8字节整数

在PHP(比特币)中读取8字节整数,php,bitcoin,Php,Bitcoin,我正在尝试读取比特币交易的值- 维基上说它是一个8字节的整数,但我在解包中尝试过的任何东西都没有给出正确的十进制值 我已经能够从事务中读取除输出值之外的所有其他内容-考虑到其他字段,我已经设法用正确的值解析了所有列,看起来我读取的是正确的8字节 与: 及 这应该是500和0.0691375。作为PHP函数的文档说明,如果试图解包长度等于PHP本机整数大小的无符号值(即32或64位,具体取决于PHP的编译方式),可能会发生奇怪的事情: “请注意,PHP在内部将整数值存储为有符号。如果您解压缩一个大

我正在尝试读取比特币交易的值-

维基上说它是一个8字节的整数,但我在解包中尝试过的任何东西都没有给出正确的十进制值

我已经能够从事务中读取除输出值之外的所有其他内容-考虑到其他字段,我已经设法用正确的值解析了所有列,看起来我读取的是正确的8字节

与:


这应该是500和0.0691375。

作为PHP函数的文档说明,如果试图解包长度等于PHP本机整数大小的无符号值(即32或64位,具体取决于PHP的编译方式),可能会发生奇怪的事情:

“请注意,PHP在内部将整数值存储为有符号。如果您解压缩一个大的无符号长文件,并且它的大小与PHP内部存储的值相同,则即使指定了无符号解压缩,结果也将是负数。”

可以说,这是一个PHP错误:如果我要求一个无符号值,我很希望得到一个无符号值,即使它必须在内部表示为浮点

在任何情况下,解决这一“怪癖”的一种方法是将二进制字符串解包成更小的块,例如每个块8或16位,然后手动重新组装,如下所示:

$bin=pack('H*','00743ba40b000000');
$words=array_reverse(解包('v*',$bin));
$n=0;
foreach($words作为$word){

$n=(1您在这里使用的
$data
是什么?嗯,该页面的哪个部分是二进制数据?原始事务看起来仍然像JSON。您必须自己从网络下载事务才能获得完整的二进制版本,该网站只解释格式,不提供二进制版本。为了简单起见,我已将二进制转换为十六进制,将十六进制添加到我的问题中,并将其转换回二进制。@PeterO。我无法更改方式这些数字是存储的——这是既定协议的一部分。谢谢——在你发布之前,我用BC Math成功地让它工作了,但我更喜欢你的版本,因为它不需要库,而且因为我是新用户,我不能再发布5个小时——答案被接受。只需注意:比特币会将数字膨胀,应该是500-您可能希望将a/100000000粘贴在其中。确实如此。虽然如果您希望避免舍入错误,您可能希望跳过
/100000000
,只将值存储为的整数,而不是BTC的分数。
$bin = hex2bin('00743ba40b000000');
$value = unpack('lvalue', $bin);
// 'value' => int -1539607552
$bin = hex2bin('d67e690000000000');
$value = unpack('lvalue', $bin);
// 'value' => int 6913750