我需要在php中做一些大数值的操作。我不得不在bcmath和gmp之间做出选择,这似乎是这类东西的主要库。我需要逆模方法,这在bcmath
库中是不可用的。所以我用的是GMP
。
现在我需要生成一个介于0和2^159-1之间的随机安全数。但是:gmp_random_bits
仅在php>=5.6.3中可用gmp_random_range
仅在php>=5.6.3中可用gmp_random
不允许我精确地指定位的数量(以及每个羔羊的位是多少,谁使用这种单元?)
我试着用openssl_random_pseudo_bytes
生成这个数字。我只能用字节数,但我试过了。唯一问题:openssl_random_pseudo_bytes(20)
返回字符串bindec(openssl_random_pseudo_bytes(20))
返回0hexdec(bin2hex(openssl_random_pseudo_bytes(20))
返回0gmp_import
仅在php>=5.6.1中可用
所以,我放弃了,尝试将我的php升级到php5.6。基于this我做了:
sudo add-apt-repository ppa:ondrej/php
sudo apt-get update
sudo apt-get upgrade
sudo apt-get install php5.6
sudo service apache2 restart
但是如果我运行
phpinfo()
,显示的php版本仍然是5.9.9。求求你,救命!我绝望了。谢谢!
最佳答案
以下应适用(在5.5.9中测试):
// gmp_init will interpret argument as hexadecimal when first two chars are 0x or 0X
$g = gmp_init( '0x' . bin2hex( openssl_random_pseudo_bytes( 20 ) ) );
echo gmp_strval( $g );
这使用
bin2hex()
。bindec()
有点混乱,因为它只接受1和0的字符串,但不需要以bindec()
开头,因为gmp_init()
将直接接受十六进制参数。bindec()
还将在输入超过PHP_INT_MAX
时输出浮点值,如果输入到gmp_init()
则会导致不希望的结果。但由于表示大量是您想要使用gmp的原因,因此首先不可能使用bindec()
。不相关,根据OP的评论:
最后,在您的一个示例中,您尝试调用
hexdec()
,bin2hex()
,bindec()
的顺序:hexdec(bin2hex(bindec(openssl_random_pseudo_bytes(20)))
没有意义,因为这试图先将二进制转换为十进制,然后将二进制转换为十六进制。
但是,如我上面的例子所示,仅仅使用
bin2hex()
就足够了,它与bindec()
相反,接受原始二进制数据并且没有PHP_INT_MAX
限制。作为替代方案,您还可以使用
unpack()
:$g = gmp_init( '0x' . unpack( 'H*', openssl_random_pseudo_bytes( 20 ) )[ 1 ] );
echo gmp_strval( $g );