【Go】IP地址转换:数字与字符串之间高效转换
转载:https://blog.thinkeridea.com/201903/go/ip2long.html
IP 地址库中 IP 地址的保存格式一般有两种,一种是点分十进制形式(192.168.1.1),另一种是数字形式(3232235777),应用中,经常需要在这两种格式之间做转换。
针对这一个问题我在 exnet 扩展包里面实现可两者的转换的快捷方法:
func IP2Long(ip net.IP) (uint, error)
IP2Long 把 net.IP 转为数值func Long2IP(i uint) (net.IP, error)
Long2IP 把数值转为 net.IPfunc IPString2Long(ip string) (uint, error)
IPString2Long 把 ip 字符串转为数值func Long2IPString(i uint) (string, error)
Long2IPString 把数值转为 ip 字符串
使用示例:
package main
import (
"fmt"
"net"
"reflect"
"github.com/thinkeridea/go-extend/exnet"
)
func main() {
ip := "192.168.1.1"
n, _ := exnet.IPString2Long(ip)
s, _ := exnet.Long2IPString(n)
fmt.Println(n, s == ip)
Ip1 := net.ParseIP(ip) // 会得到一个16字节的byte,主要为了兼容ipv6
n, _ = exnet.IP2Long(Ip1)
Ip2, _ := exnet.Long2IP(n)
fmt.Println(n, reflect.DeepEqual(Ip1[12:], Ip2))
}
那么是如何将点分十进制的IP地址转为数字?
IPv4 地址有4个字节,样式如下:
MSB————–LSB
b4 b3 b2 b1
每个字节表示的范围:
- byte4: 4294967296(1<<32)
- byte3: 16777216(1<<24)
- byte2: 65536(1<<16)
- byte1: 256(1<<8)
通用公式:b4<<24 | b3<<16 | b2<<16 | b1
例如,222.173.108.86
转换方法:222<<24 | 173<<16 | 108<<8 | 86 = 3735907414
再例如,1.0.1.1
转换方法:1<<24 | 0<<16 | 1<<8 | 1 = 16777473
exnet 中实现如下:
// IPString2Long 把ip字符串转为数值
func IPString2Long(ip string) (uint, error) {
b := net.ParseIP(ip).To4()
if b == nil {
return 0, errors.New("invalid ipv4 format")
}
return uint(b[3]) | uint(b[2])<<8 | uint(b[1])<<16 | uint(b[0])<<24, nil
}
把数值转换为字符串的逻辑翻转过来即可, exnet 中实现如下:
// Long2IPString 把数值转为ip字符串
func Long2IPString(i uint) (string, error) {
if i > math.MaxUint32 {
return "", errors.New("beyond the scope of ipv4")
}
ip := make(net.IP, net.IPv4len)
ip[0] = byte(i >> 24)
ip[1] = byte(i >> 16)
ip[2] = byte(i >> 8)
ip[3] = byte(i)
return ip.String(), nil
}
转载:
本文作者: 戚银(thinkeridea)
本文链接: https://blog.thinkeridea.com/201903/go/ip2long.html
版权声明: 本博客所有文章除特别声明外,均采用 CC BY 4.0 CN协议 许可协议。转载请注明出处!
【Go】IP地址转换:数字与字符串之间高效转换的更多相关文章
- C++中数字与字符串之间的转换 scanf string总结(复习必读)
1 string的scanf读入操作 C++里面控制台输入直接使用cin操作就可以了:或者getline(istringstream,string); 字符和数字加减就是字符的ASCII码和数字直接加 ...
- C++中数字与字符串之间的转换,别人的,
C++中数字与字符串之间的转换 1.字符串数字之间的转换 (1)string --> char * string str("OK"); char * p = st ...
- C++中数字与字符串之间的转换
原文地址:http://www.cnblogs.com/luxiaoxun/archive/2012/08/03/2621803.html 1.字符串数字之间的转换 (1)string --> ...
- C++中数字与字符串之间的转换(转)
http://www.cnblogs.com/luxiaoxun/archive/2012/08/03/2621803.html 1.字符串数字之间的转换 (1)string --> char ...
- C++中数字与字符串之间的转换(使用CString.Format或者sprintf)
1.字符串数字之间的转换 (1)string --> char * string str("OK"); char * p = str.c_str(); (2)char ...
- [C/C++] C/C++中数字与字符串之间的转换
在C中: 方法: 1.C标准库中的sprintf, sscanf 2.C标准库还提供了 atoi, atof, atol, atoll(C++11标准) 函数将字符串转换成int,double, lo ...
- js 中数字与字符串之间的转换
数字转换为字符串 var num = 123: 1.num.toString 2."" + num 3.String(num) 将数字转化为格式化后的字符串 num.toFixe ...
- boost-使用format和lexical_cast实现数字和字符串之间的转换
使用boost的format可以实现数字到string的格式化转换,boost的lexical_cast可以实现string到数值的转换,eg: #include "boost/format ...
- 数字与字符串之间的转换以及%f与%lf的输入输出用法区别
1.C++字符串与C字符串的转换: (1)string --> char * string str("OK"); strcpy(p,str.c_str());//p是char ...
随机推荐
- java中接口和继承的区别
实际概念区别:区别1:不同的修饰符修饰(interface),(extends)区别2:在面向对象编程中可以有多继承!但是只支持接口的多继承,不支持'继承'的多继承哦而继承在java中具有单根性,子类 ...
- fiddler抓包工具总结
Fiddler 抓包工具总结 Fiddler是一个蛮好用的抓包工具,可以将网络传输发送与接受的数据包进行截获.重发.编辑.转存等操作.也可以用来检测网络安全.反正好处多多,举之不尽呀!当年学习的时候也 ...
- 哈夫曼(Huffman)树和哈夫曼编码
一.哈夫曼(Huffman)树和哈夫曼编码 1.哈夫曼树(Huffman)又称最优二叉树,是一类带权路径长度最短的树, 常用于信息检测. 定义: 结点间的路径长度:树中一个结点到另一个结点之间分支数目 ...
- PHP单一文件入口框架简析
<?php /** * PHP单一文件框架设计简析 * 1.MVC架构实现 * 2.URL路由原理 */ //URL路由原理 /** * 路由作用 * 获取url中的c和a变量,执行c类对应的方 ...
- js基础知识:字面量 关键字和保留字
js中的字面量概念我的理解就是:字体表面的常量 如:数字 100, 字符串 "ssss"或'ssss' 布尔值:false ,正则 以及null对象. 这些都是常量. 关键字: ...
- JAVA的 IO NIO AIO笔记
IO linux内核将所有外部设备都看做一个文件来操作,对一个文件的读写会调用内核系统命令,放回一个file descriptor(文件描述符), 对一个socket的读写也会有相应 ...
- mac上terminal_问题_1117
(1)安装Homebrew /usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install ...
- js every some 遍历函数理解
1.every let arr = [0, 1, 2, 3, 4, 5]; let result = arr.every((item, index) => { return item >= ...
- 《Node.js高级编程》之Node 核心API基础
Node 核心API基础 第三章 加载模块 第四章 应用缓冲区 第五章 事件发射器模式简化事件绑定 第六章 使用定时器制定函数执行计划 第三章 加载模块 本章提要 加载模块 创建模块 使用node_m ...
- JAVA编程思想的理解
1)POP--面向过程编程(Process-oriented programming ): 面向过程编程是以功能为中心来进行思考和组织的一种编程方法,它强调的是系统的数据被加工和处理的过程,在程序 ...