Python中IPv4地址转换为整数的原理与实践
本文详解Python中将IPv4地址转换为整数的原理,通过struct模块打包字节串并转为整数,实现数据库存储空间的节省。同时对比了传统inet_aton/ntoa函数与兼容IPv6的inet_pton/ntop API,指出在IPv6普及背景下,VARCHAR存储可能更具通用性。
背景与问题提出
背景
近期有读者询问为何数据库中建议使用int类型存储IP地址。从2020年的视角来看,这一做法已略显过时。主要原因包括磁盘存储成本大幅降低,以及IPv6地址无法直接兼容这种整型存储方案。
接下来,我们将深入探讨IPv4地址转换为整数的具体原理及其带来的实际收益。
IPv4转整数的原理
转换的原理
IPv4地址由四个部分组成,格式为0.0.0.0,每个部分的取值范围是0到255。这意味着每个部分只需一个字节即可存储,四个部分合计4个字节,恰好对应整型(int)的大小。
转换的第一步是将IP地址的各部分转换为字节,并拼接成一个4字节的字符串。
import struct
def aton(ip_address: str) -> bytes:
result = []
for i in ip_address.split('.'):
result.append(struct.pack("!B", int(i)))
return b''.join(result)
第二步是将该字节字符串转换为整数。
In [2]: aton("127.0.0.1")
Out[2]: b'\x7f\x00\x00\x01'
In [3]: int.from_bytes(b'\x7f\x00\x00\x01','big')
Out[3]: 2130706433
通过上述步骤,我们成功将IPv4地址转换为整数。完整的实现代码如下。
import struct
def aton(ip_address: str) -> bytes:
result = []
for i in ip_address.split('.'):
result.append(struct.pack("!B", int(i)))
return b''.join(result)
if __name__ == "__main__":
bts = aton("127.0.0.1")
print(int.from_bytes(bts, 'big'))
运行效果如下。
python3 main.py
2130706433
转换的收益与限制
转换的收益与限制
若不进行转换,使用varchar类型存储IPv4地址通常需要15个字节(3*4 + 3个分隔符);而转换为整数仅需4个字节,从而节省了磁盘空间,但可能会增加少量的CPU处理时间。
目前IPv6已成为主流,其地址长度从IPv4的4字节扩展至16字节,int类型已无法满足需求。为了统一处理IPv4和IPv6,推荐使用varchar类型存储IP地址。
传统与新型API对比
inet_aton 与 inet_ntoa
这对函数是IPv4时代的经典转换工具,目前看来已逐渐过时。
1、inet_aton:将IP地址转换为数字。
In [4]: socket.inet_aton("127.0.0.1")
Out[4]: b'\x7f\x00\x00\x01'
2、inet_ntoa:将数字转换回IP地址。
In [5]: socket.inet_ntoa(b'\x7f\x00\x00\x01')
Out[5]: '127.0.0.1'
inet_pton 与 inet_ntop
这是一组新的API,兼容IPv4和IPv6两种协议。
In [6]: socket.inet_pton(socket.AF_INET6,"5aef:2b::8")
Out[6]: b'Z\xef\x00+\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x08'
In [7]: socket.inet_ntop(socket.AF_INET6,b'Z\xef\x00+\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x08')
Out[7]: '5aef:2b::8'
In [8]: socket.inet_pton(socket.AF_INET,"127.0.0.1")
Out[8]: b'\x7f\x00\x00\x01'
In [9]: socket.inet_ntop(socket.AF_INET,b'\x7f\x00\x00\x01')
Out[9]: '127.0.0.1'
以上即为Python中IP地址转换为整数的详细内容,更多关于Python IP地址转换的资料请关注本站其它相关文章!
本站声明
本文内容仅供参考,不代表本站观点。转载或引用请注明出处。如发现内容问题,请通过联系我们页面反馈。













