由项目中一个hash2int函数引发的思考
hash2int
/**
* 计算一个字符串的md5折算成int返回
* @param type $str
* @return type
*/
function hash2int($str) {
$md5str = md5($str, true);
$one = unpack('l', substr($md5str, 0, 4));
$two = unpack('l', substr($md5str, 4, 4));
$three = unpack('l', substr($md5str, 8, 4));
$four = unpack('l', substr($md5str, 12, 4));
return current($one) + current($two) + current($three) + current($four);
}
思考一:这个函数有没有优化的空间,直接上代码
function hash2int2($str) {
$md5str = md5($str, true);
$arr = unpack('la/lb/lc/ld', $md5str);
return array_sum($arr);
}
效率大约是上一个函数的4倍(当然这种程度的优化对于一个设计到db等的大项目的效率影响很小)
思考二:pack/unpack在php中的使用
首先熟悉几个概念
计算机当中通常采用的自己存储方式(字节序)有:大端和小端
大端序(网络字节序):①多字节传输时,先传高字节;②存储时高位字节在低地址
小端序:①多直接传输时,先传低位字节;②存储时低位字节放在低地址
栗子:0x12345678
大端序:0x12 0x34 0x56 0x78
小端序:0x78 0x56 0x34 0x12
主机字节序:本机的字节序
pack的参数:
格式字符翻译 a -- 将字符串空白以 NULL 字符填满 A -- 将字符串空白以 SPACE 字符 (空格) 填满 h -- 16进制字符串,低位在前以半字节为单位 H -- 16进制字符串,高位在前以半字节为单位 c -- 有符号字符 C -- 无符号字符 s -- 有符号短整数 (16位,主机字节序) S -- 无符号短整数 (16位,主机字节序) n -- 无符号短整数 (16位, 大端字节序) v -- 无符号短整数 (16位, 小端字节序) i -- 有符号整数 (依赖机器大小及字节序) I -- 无符号整数 (依赖机器大小及字节序) l -- 有符号长整数 (32位,主机字节序) L -- 无符号长整数 (32位,主机字节序) N -- 无符号长整数 (32位, 大端字节序) V -- 无符号长整数 (32位, 小端字节序) f -- 单精度浮点数 (依计算机的范围) d -- 双精度浮点数 (依计算机的范围) x -- 空字节 X -- 倒回一位 @ -- 填入 NULL 字符到绝对位置
关于pack和unpack推荐3篇博客,写得非常好
http://my.oschina.net/goal/blog/195749
http://my.oschina.net/goal/blog/202378
http://my.oschina.net/goal/blog/202381
后续我会结合自己项目当中php跟C模块通过Nshead协议的交互来补充这块
思考三:有各种数字想到了ip2long这个函数
php中的ip2long函数的原理:将每一段看成256进制的数字
function ip2int($ip) {
list($ip1, $ip2, $ip3, $ip4) = explode(".", $ip);
return ($ip1 << ) | ($ip2 << ) | ($ip3 << ) | ($ip4);
}
问题就出现了,2int之后可能出现负数,所以我们一般使用 sprintf('%u',ip2long($ip))
php是只支持有符号的整数的,32 64的系统所支持最大的整型数是不同的,所以在不同操作系统使用ip2long的时候得到的结果可能是不一样的,这个问题值得注意
可以用sprintf('%u',ip2long($ip)),需要注意的是,sprintf返回的都是字符串
function dotip2uint($cip) {
$dotips = explode('.', $cip, 4);
return intval($dotips[0]) * 16777216 + intval($dotips[1]) * 65536 + intval($dotips[2]) * 256 + intval($dotips[3]);
}
由项目中一个hash2int函数引发的思考的更多相关文章
- 转:一个Sqrt函数引发的血案
转自:http://www.cnblogs.com/pkuoliver/archive/2010/10/06/1844725.html 源码下载地址:http://diducoder.com/sotr ...
- 一个Sqrt函数引发的血案(转)
作者: 码农1946 来源: 博客园 发布时间: 2013-10-09 11:37 阅读: 4556 次 推荐: 41 原文链接 [收藏] 好吧,我承认我标题党了,不过既然你来了, ...
- 【转载】一个Sqrt函数引发的血案
转自:http://www.cnblogs.com/pkuoliver/archive/2010/10/06/sotry-about-sqrt.html 源码下载地址:http://diducoder ...
- 一个Sqrt函数引发的血案
源码下载地址:http://diducoder.com/sotry-about-sqrt.html 好吧,我承认我标题党了,不过既然你来了,就认真看下去吧,保证你有收获. 我们平时经常会有一些数据运算 ...
- 由一个DAOHelper类引发的思考
这是一篇发牢骚的文章,可以这么说吧.DAOHelper究竟有什么用呢?用我自己的话去理解,DAOHelper的存在正是敏捷开发的产物,即快速开发. 我们究竟能从项目中学到什么呢?有的人可能会说,从一个 ...
- MVC系列——一个异常消息传递引发的思考
前言:最近在某个项目里面遇到一个有点纠结的小问题,经过半天时间的思索和尝试,问题得到解决.在此记录一下解决的过程,以及解决问题的过程中对.net里面MVC异常处理的思考.都是些老生常谈的问题,不多说, ...
- 由struts2中配置使用servlet引发的思考和复习
Struts2拦截器到底拦截了什么? 关于struts2中的拦截器,首先再次理解其实只能过滤其中访问的action的映射!再者,因为struts中的action其实就是起到替代servlet作用的,所 ...
- Dynamics CRM中一个查找字段引发的【血案】
摘要: 本人微信和易信公众号: 微软动态CRM专家罗勇 ,回复267或者20180311可方便获取本文,同时可以在第一间得到我发布的最新的博文信息,follow me!我的网站是 www.luoyon ...
- Qt项目中main主函数及其作用
http://c.biancheng.net/view/1821.html main.cpp 是实现 main() 函数的文件,下面是 main.cpp 文件的内容. #include "w ...
随机推荐
- CGAffineTransform方法汇总
CGAffineTransform是二维的仿射变换,可以进行位移,旋转,缩放,CGAffineTransform实际上是一个矩阵. CGAffineTransform { CGFloat a, b, ...
- 安卓--selector简单使用
selector ---选择器 在App的使用中经常能看到selector的身影 如:一个按键看上去白色或者其它颜色,可能是一张图片 按下去又显示其它的颜色或者另外一张图片 这里使用shape配合使用 ...
- OC与JS的交互
现在APP的开发已经不局限于原生开发,很多都是原生+html5这种混合开发 我们可以通过webView这个控件,实现混合开发. 1.首先你需要创建一个html页面 <html> <h ...
- 让UILabel的文字顶部对齐
参考资料 http://stackoverflow.com/questions/1054558/how-do-i-vertically-align-text-within-a-uilabel 方法一 ...
- CSS Float 以及相关布局模式
float 取值 属性 值 描述 left 向左浮动 right 向右浮动 none 默认值 inherit 继承 看一个栗子 红色线框代表父元素 脱离文档流,其实也没有完全脱离,会被 ...
- AEAI DP按钮权限配置说明
1 背景概述 AEAI DP3.5版本以后支持对按钮权限进行灵活的管理配置,本文对配置过程进行详细说明,为相关使用人员提供指导和参考. 2 预期读者 数通畅联技术人员 AEAI DP开发平台使用人员 ...
- 在ROS中使用Python3
Use Python3 in ROS. 以下内容在Ubuntu 16.04 x64和ROS kinetic中测试通过 事实上,只要在.py文件加上python3的shebang,rosrun的时候就会 ...
- informatica 学习日记整理
1. INFORMATICA CLIENT的使用 1.1 Repository Manager 的使用 1.1.1 创建Repository. 前提: a.在ODBC数据源管理器中新建一个数据源连接至 ...
- ORACLE口令管理
口令文件介绍 在ORALCE数据库系统中,用户如果要以特权用户身份(SYS/SYSDBA/SYSOPER)登录ORALCE数据库可以有两种身份验证的方法:即使用与操作系统集成的身份验证或使用ORALC ...
- Flume应用场景及架构原理
Flume概念 Flume是一个分布式.可靠.和高可用的海量日志聚合的系统,支持在系统中定制各类数据发送方,用于收集数据:同时,Flume提供对数据进行简单处理,并写到各种数据接受方(可定制)的能力. ...