php 超过64位进制和10进制的转换
有时候想把一个很大的数尽量用更少的空间存储起来,那么就可以采用很大的进制来存储它,比如说,一个大于等于10小于等于16数字使用10进制就需要两位,使用16进制就只需要1位,那就等于帮程序省了一位的空间,数字越大,进制越高,效果也就越明显。
举例如下:
1000000的转换比较 | 二进制 | 八进制 | 十进制 | 十六进制 |
转换结果 |
11110100001001000000
|
3641100
|
1000000 |
f4240
|
占用存储长度 |
20
|
7
|
7 |
5
|
现在我们可以看到,十六进制能省下2个长度,然后我们能不能得到一个更高进制?那就能省更多空间了,且看代码
<?php // need bcmath extension function binaryTo(int $num = 0) { $dict = '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ,./?<>{}[]|()'; $to = strlen($dict); $ret = ''; do { $ret = $dict[bcmod($num, $to)] . $ret; //bcmod取得高精确度数字的余数。 $num = bcdiv($num, $to); //bcdiv将二个高精确度数字相除。 } while ($num > 0); return $ret; } function binaryFrom(string $num = '') { $num = strval($num); $dict = '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ,./?<>{}[]|()'; $from = strlen($dict); $len = strlen($num); $dec = 0; for($i = 0; $i < $len; $i++) { $pos = strpos($dict, $num[$i]); $dec = bcadd(bcmul(bcpow($from, $len - $i - 1), $pos), $dec); } return $dec; } var_dump(binaryTo(1000000)); var_dump(binaryFrom('2rWp'));
这个代码可能会报错,如果报错请检查是不是没开启 bcmath 扩展,没有这个扩展的你就装一下,sudo apt search 然后install 一下
此时我们就可以把这个表格更新了,我们看到现在使用这个函数得到的进制结果是 2rWp 那么长度就是4位。
表格更新如下:
1000000的转换比较 | 二进制 | 八进制 | 十进制 | 十六进制 | 七十五进制 |
转换结果 | 11110100001001000000 | 3641100 | 1000000 | f4240 |
2rWp
|
占用存储长度 | 20 | 7 | 7 | 5 | 4 |
我们可能觉得7个长度缩减到4个长度,这并不算什么,但是如果你有一个很大数据量的存储文本,你存储了大量的这种id int型的数据,那么就会占用很大的空间,此时你采用这种方式转换存储一下,发现文件能减少30%左右,那这个时候该文件的读写就能快很多,能减少服务器各方面(硬盘空间 内存空间等)压力,数据量越多,其效果就越明显。
当然这里面有副作用,比如我添加的数据需要转换一次回到10进制,才能给前台使用,查询的时候也要先转为75进制进行查询,特殊格式如果用到了]})这种的时候可能会影响你的业务逻辑,那你需要根据自身业务情况处理一下,或者换其他的符号作为进制符号。