今天在做的事情是将一个as3项目的部分代码移植到PHP中来,记录下移植过程中遇到的两个问题。
1,AS3中String类的charCodeAt函数是返回字符的unicode编码,而在PHP中并没有直接与之对应的库函数,可以用下面这个函数做替代:
代码
<!--<br/ /><br/ />Code highlighting produced by Actipro CodeHighlighter (freeware)<br/ />http://www.CodeHighlighter.com/<br/ /><br/ />--><?php
functionuniord($str,$from_encoding=false){
$from_encoding=$from_encoding?$from_encoding:'UTF-8';
if(strlen($str)==1)
returnord($str);
$str=mb_convert_encoding($str,'UCS-4BE',$from_encoding);
$tmp=unpack('N',$str);
return$tmp[1];
}
$str="12345";
$result=array();
for($i=0,$l=mb_strlen($str,'utf-8');$i<$l;++$i){
$result[]=uniord(mb_substr($str,$i,1,'utf-8'));
}
echojoin(",",$result);
?>
2,PHP的二进制位移操作
PHP主要是设计于文本操作的,其实PHP不适合做数学运算,效率也不高,不过因为AS3项目中有大量的二进制位移操作,在移植到PHP来时遇到了麻烦。
因为PHP只有32位有符号整数,没有64位长整型,也没有无符号整数。其整型的范围是-231-1~231,超出这个范围的,将被解释为浮点数。因此,0xFFFFFFFF,直接打印,显示的是4294967295,及232:
<!--<br/ /><br/ />Code highlighting produced by Actipro CodeHighlighter (freeware)<br/ />http://www.CodeHighlighter.com/<br/ /><br/ />-->>>0xFFFFFFFFF
4294967295
>>gettype(0xFFFFFFFF)
'double'
而在32位有符号整型中,0xFFFFFFFF应表示-1:
<!--<br/ /><br/ />Code highlighting produced by Actipro CodeHighlighter (freeware)<br/ />http://www.CodeHighlighter.com/<br/ /><br/ />-->>>(int)0xFFFFFFFFF
-1
而PHP不支持浮点数的二进制位移操作,如果要进行,会先转换为整型,最后的结果,也将按照整型来返回:
<!--<br/ /><br/ />Code highlighting produced by Actipro CodeHighlighter (freeware)<br/ />http://www.CodeHighlighter.com/<br/ /><br/ />-->>>1<<31
-2147483648
>>1<<30
1073741824
>>1<<32
1
>>0xFFFFFFFF>>1
-1
同时PHP的向右位移操作,高位会填充符号位,而且PHP没有提供类似Java的>>>来强制填充0:
<!--<br/ /><br/ />Code highlighting produced by Actipro CodeHighlighter (freeware)<br/ />http://www.CodeHighlighter.com/<br/ /><br/ />-->>>1<<32
1
>>0xFFFFFFFF>>1
-1
>>0xFFFFFFFF>>2
-1
>>0xFFFFFFFF>>3
-1
>>0xFFFFFFFF>>31
-1
如何解决这个问题呢,我考虑过使用BCMath数学函数库,直接处理字符串表示的整数,或者是GMP/BigInt扩展等。
不过我想既然使用字符串,那么我可以字符串地彻底一些,把数字转换成32个二进制的字符串,再手工填充0,最后转换回来。
逻辑移位的代码如下:
代码
<!--<br/ /><br/ />Code highlighting produced by Actipro CodeHighlighter (freeware)<br/ />http://www.CodeHighlighter.com/<br/ /><br/ />--><?php
/**
*无符号32位右移
*@parammixed$x要进行操作的数字,如果是字符串,必须是十进制形式
*@paramstring$bits右移位数
*@returnmixed结果,如果超出整型范围将返回浮点数
*/
functionshr32($x,$bits){
//位移量超出范围的两种情况
if($bits<=0){
return$x;
}
if($bits>=32){
return0;
}
//转换成代表二进制数字的字符串
$bin=decbin($x);
$l=strlen($bin);
//字符串长度超出则截取底32位,长度不够,则填充高位为0到32位
if($l>32){
$bin=substr($bin,$l-32,32);
}elseif($l<32){
$bin=str_pad($bin,32,'0',STR_PAD_LEFT);
}
//取出要移动的位数,并在左边填充0
returnbindec(str_pad(substr($bin,0,32-$bits),32,'0',STR_PAD_LEFT));
}
/**
*无符号32位左移
*@parammixed$x要进行操作的数字,如果是字符串,必须是十进制形式
*@paramstring$bits左移位数
*@returnmixed结果,如果超出整型范围将返回浮点数
*/
functionshl32($x,$bits){
//位移量超出范围的两种情况
if($bits<=0){
return$x;
}
if($bits>=32){
return0;
}
//转换成代表二进制数字的字符串
$bin=decbin($x);
$l=strlen($bin);
//字符串长度超出则截取底32位,长度不够,则填充高位为0到32位
if($l>32){
$bin=substr($bin,$l-32,32);
}elseif($l<32){
$bin=str_pad($bin,32,'0',STR_PAD_LEFT);
}
//取出要移动的位数,并在右边填充0
returnbindec(str_pad(substr($bin,$bits),32,'0',STR_PAD_RIGHT));
}
?>
分享到:
相关推荐
每日学习笔记11111111111111
JS学习笔记
已整理好基础版和高级版笔记 导出为pdf 和html 格式 界面清晰美观,均有详细目录
每日更新机器学习笔记、代码及其它内容。.zip
Study Notes日常学习笔记记录推荐使用打开Markdown简单Markdown语法整理初版日期:2021-3-28Allegro creat Gerber filesCreated date:2021-4-4GitCreated date:2021-4-4
spring学习笔记 很详细的学习笔记分享给大家,大家可以看看,绝对物有所值
stone的终身学习笔记 前言 09年 渣3本毕业,金融危机 09~10年 跑业务打杂工养活自己 10~12年 私企,企业资源管理ERP(VF、VB) 12~17年 国企,企业办公自动化OA(.NET、JavaScript) 17~20年 阿里影业,影城售票系统...
MLDL 研究生预备知识学习笔记,包含李宏毅深度学习与数字图像处理。 深度学习笔记在基础上添加自己的理解,纯自用。 MLDnotes 深度学习笔记 papernotes 论文笔记与相关知识 plans 每日计划
javascript_study 每日代码汇总,学习笔记及页面仓库
机器学习课程笔记完整版 机器学习 目录 机器学习算法课程定位、目标 定位 课程以算法、案例为驱动的学习,伴随浅显易懂的数学知识 作为人工智能领域(数据挖掘/机器学习方向)的提升课程,掌握更深更有效的解决...
此笔记为作者在有java基础的前提下,自学B站马士兵python视频所记,内容简洁方便看完视频后日后回顾,也适合自学B站马士兵python视频每日回顾。
学习英语需要积累每日一句,多多练习,多多积累,多多交流
每日英语词典 1-3期知识点 笔记 《Daily English Dictation》第1-3期知识点 1、(无听力讲解) 2、(讲解看截图)
这本书在我学习seo的过程中帮助很大,学到了很多的有用信息
算法学习笔记 通过leetcode的每日打卡,熟悉的分类算法;记录下学习过的算法题,整理成markdwn文本;并根据打卡情况制定计划,着重学习自己很难甚至没有理解的算法。习惯用Jupyter Notebook进行学习,刚好notebook...
Collection学习笔记Collection集合概述Collection集合常用方法Collection集合的遍历(迭代器)集合的使用样例 Collection集合概述 是单例集合的顶层接口 它提供了更具体的子接口的实现,如set和list. Collection集合...
每日一学 字典查找类似hash表,速度远超过for遍历列表。 for index,value in enumerate(s): .get函数两个参数时,第二个应重新字典引用,见下面使用方法 arabic += ara_rom_dict.get(s[index-1:index+1],ara_rom_...
目录 算法 每日更新 计算机操作系统 数据结构 前端工具 组件库 功能库 javascript React 打字稿 实用程序 emacs 吉特 多路复用器
在Hacktiv8的全栈新手训练营期间,进行个人学习笔记(每日挑战,实时代码等)。 工具: 文本编辑器:Visual Studio Code 终端机:Git bash,MacOS终端机,iTerm 版本控制:Git 回购经理:Github 包管理器:NPM...
CDGA学习笔记就是所有知识点的总结,按章节划分,有利于建立属于自己的数据知识体系, 重点语境图我也都截出来了,可直接打印,进行背诵, 最后是DAMA视频精讲资料。 这次可谓史上最全资料,实际学习过程中可以选择...