由于数字的查询、传输效率要优于字符串,所以我将之前用字符串存储ip地址的方案彻底改为使用数字型来存储ip地址。

直接给函数后面说过程
var obj={
ip_number:function(ip){ // ip地址转数字函数,我们这里就随便找一个ip 27.115.124.38
var num = 0;
ip = ip.split("."); // 将ip字符串转为数组[27,115,124,38]
num = Number(ip[0]) * 256 * 256 * 256 + Number(ip[1]) * 256 * 256 + Number(ip[2]) * 256 + Number(ip[3]); // 注释请看后面
// 或者使用>>、<<、>>>方法
// num=Number(ip[0])<<24 + Number(ip[1])<<16 + Number(ip[2])<<8 + Number(ip[3])
num = num >>> 0; // 注释请看后面
return num;
},
number_ip:function(num){// 数字转ip函数
var ip;
var arr = new Array();
arr[0] = (num >>> 24) >>> 0;
arr[1] = ((num << 8) >>> 24) >>> 0;
arr[2] = (num << 16) >>> 24;
arr[3] = (num << 24) >>> 24;
ip = String(tt[0]) + "." + String(tt[1]) + "." + String(tt[2]) + "." + String(tt[3]);
// 或者使用数组的join方法
// ip =arr.join(".")
return ip;
}
}
module.exports=obj;
运算符>>、<<、>>>
在js里默认是以32位浮点型来存储数字的,也就是不超32位的数字型变量在计算机内部都是32位的数据。【这个很重要,涉及到后面的推位计算】
比如1
的存储就是000000000000000000000000000000001
,这其实刚好对上的ip地址的存储,ip地址也是设计的32位计算的。我们把32位分成4分,每份占8位00000000-11111111
对应的0-255
刚好是我们ip地址每位的0到255。这也是我们能把ip地址按数字来存储的前提,有了这个背景我们就方便使用推位来对ip地址进行数字和字符串的转换了。
2147483648>>8
>>
将二进制向右推,推空的位补零
// 比如1的二进制是00000000000000000000000000000001向右推2位0000000000000000000000000000000,右边的2位被推出去了,左边空出来的2位补零,返回新的数据
1>>2
// 结果是0
这里我们是10进制直接推,得到的结果还是十进制
// 比如1的二进制是10000000000000000000000000000000向右推2位0010000000000000000000000000000,右边的2位被推出去了,左边空出来的2位补零,返回新的数据
2147483648>>2
// 结果是536870912
<<
将二进制向左推,推空的位补零。
这个同理,就不展开了,将左右推结合起来就方便对ip地址进行数据和字符串的转换了。
>>>
将二进制向右推,如果是负数首位会先置零,运算符执行无符号右移位运算。
对于负数来说,无符号右移将使用 0 来填充所有的空位,同时会把负数作为正数来处理,所得结果会非常大,所以使用无符号右移运算符时要特别小心,避免意外错误。
案例当中只是起到了保证正数的作用,不用其实也可以。
数据类型
js默认的数值类型使用的是32位的浮点型,所以如果你使用的是别的编程语言,转换函数的推位
就需要做相应的调整。
文章首发:www.ic365club.com
ic365club旨在共同学习,共同进步