宝塔拨测博客拨测技术博客
宝塔拨测

IP 地址怎么转成十进制?192.168.1.1 等于 3232235777 的换算与三个坑

IPv4 地址本质是一个 32 位整数,192.168.1.1 只是把这个整数按四个 8 位分段、用点隔开写出来。转成十进制只有一件事:四段分别乘 256 的幂,再相加。

十进制 = 第一段×16777216 + 第二段×65536 + 第三段×256 + 第四段

代入 192.168.1.1:192×16777216 + 168×65536 + 1×256 + 1 = 3232235777。

本文用IPv4 地址转换工具实测了 7 组输入,把五路输出各自能用在什么地方、哪些写法会被拒,以及「系统认、工具不认」的整数写法都记下来。

IPv4 地址转换工具:输入 192.168.1.1,十进制 3232235777、十六进制 C0A80101、二进制 11000000.10101000.00000001.00000001,IPv6 映射与短格式分别为 0000:0000:0000:0000:0000:ffff:c0a8:0101 和 ::ffff:c0a8:0101

手算一遍:四段各占 8 位

192.168.1.1 拆开是 192、168、1、1 四个数,每个数占 8 个二进制位,取值范围 0–255。相邻两段之间差 256 倍,所以第一段的权重最大:

段位 权重 本段数值 乘积
第一段 16777216(256³) 192 3221225472
第二段 65536(256²) 168 11010048
第三段 256(256¹) 1 256
第四段 1(256⁰) 1 1
合计 3232235777

四段合起来正好 32 位,所以上限是 255.255.255.255 = 4294967295,也就是 2³²−1。实测输入 255.255.255.255,工具给出的十进制是 4294967295、十六进制 FFFFFFFF;下限 0.0.0.0 是 0。

这也解释了一个常见疑问:为什么 IP 越大、数字越大,但字符串排序会乱。 10.0.0.1 的数值比 9.0.0.1 大,按字符串排却排在前面(字符 1 小于 9)。

反向:3232235777 怎么还原成 192.168.1.1

一直除以 256、记余数,余数从后往前排就是四段:

3232235777 ÷ 256 = 12625921  余 1   → 第四段 1
12625921   ÷ 256 = 49320     余 1   → 第三段 1
49320      ÷ 256 = 192       余 168 → 第二段 168
192        ÷ 256 = 0         余 192 → 第一段 192

得到 192.168.1.1。程序里通常用位运算代替除法:取最高 8 位用 (n >>> 24) & 255,依次右移 16、8、0 位。注意 JavaScript 的位运算结果是 32 位有符号,处理 2147483647 以上的地址要先 n >>> 0 转成无符号,否则符号位会把结果变成负数。

五路输出分别是什么

输出行 192.168.1.1 的结果 用途与注意
十进制 3232235777 存库、做范围比较
十六进制 C0A80101 每段两位、大写,不带 0x 前缀
二进制 11000000.10101000.00000001.00000001 每段 8 位,带点分段
IPv6 映射 0000:0000:0000:0000:0000:ffff:c0a8:0101 ::ffff:192.168.1.1 的完整写法
IPv6 短格式 ::ffff:c0a8:0101 同一地址的压缩写法

三个容易误读的地方:

1. 十六进制省略前导零。 输入 1.2.3.4,十六进制只显示 1020304(7 位),完整值应是 01020304;输入 0.0.0.0 只显示一个 0。不是丢了位,是前导零没补。

IPv4 地址转换工具:输入 1.2.3.4,十进制 16909060,十六进制显示 1020304(前导零被省略),二进制 00000001.00000010.00000011.00000100

2. 二进制带点。 这是按四段输出的,直接粘进只认连续 32 位二进制的程序会报格式错,用前先去掉点。

3. IPv6 映射不是能访问的地址。 ::ffff:c0a8:0101 是 IPv4-mapped IPv6 的表示法,用来在 IPv6 的数据结构里标记「这其实是个 IPv4 地址」,它不是一条可以 ping 通的 IPv6 地址。想确认网站是否支持 IPv6,看的是域名的 AAAA 记录和实际拨测结果,不是看这一行——具体测法见IPv6 网站打不开怎么测?IPv6 网站测速、Ping、TCPing 三个工具分别测什么。

工具只认四段点分十进制

实测三类输入都会被拒,输入框下方出现红字「IPv4 地址格式不正确」,五行结果全部替换为「请输入合法的 IPv4 地址」:

  • 3232235777:纯整数,没有点
  • 192.168.1.256:某一段超出 0–255
  • 010.1.1.1:带前导零

IPv4 地址转换工具:输入 3232235777 后红字提示「IPv4 地址格式不正确」,五行结果都显示「请输入合法的 IPv4 地址」

工具页写明所有转换在浏览器本地完成、不上传服务器。要做反向换算,只能自己按上面的除法算,或者交给系统的解析器——而系统的判断标准和这个工具并不一样。

系统认整数,工具不认:一个真实的不一致

在 Debian 13(glibc)上实测:

输入 系统解析结果
getent ahostsv4 3232235777 192.168.1.1
Node dns.lookup("3232235777") 192.168.1.1
Node dns.lookup("010.1.1.1") 8.1.1.1(前导零按八进制)
getent ahostsv4 0x7f000001 127.0.0.1(十六进制写法)
getent ahostsv4 127.1 127.0.0.1(省略段的写法)
curl http://2130706433/ 的 Trying 127.0.0.1:80

也就是说,同一串数字在「工具校验」和「系统解析」两边结论相反:工具判它格式错,系统的 getaddrinfo 却把它当合法 IPv4 处理。前导零按八进制解释这一点尤其容易踩:010 是 8,不是 10。

对做服务端的人,这直接影响 SSRF 防护。很多代码在字符串层面拦 127.0.0.1、localhost,但 http://2130706433/、http://0177.0.0.1/、http://0x7f000001/ 这类写法能被解析器接受。可靠的做法是先解析、拿到实际 IP 再比较,而不是在原始字符串上匹配黑名单。

存数据库为什么爱用整数

把 IP 存成整数有三个实在的好处:

  1. 排序正确。 数值大小和地址先后一致,字符串排序会乱(10.0.0.1 与 9.0.0.1)。
  2. 占位固定。 点分十进制最长 15 字节且变长,整数固定 4 字节,索引更小。
  3. 范围查询能走索引。 查一个网段就是 BETWEEN 两个整数,不用做字符串前缀匹配。

有一个必须注意的边界:32 位有符号整型存不下 2147483647 以上的地址。 192.168.1.1 的 3232235777 按 32 位有符号表示是 -1062731519(3232235777 − 4294967296)。所以要存整数就选无符号:MySQL 用 INT UNSIGNED(上限正好 4294967295),或直接 BIGINT。MySQL 也自带 INET_ATON() / INET_NTOA() 做双向换算,不必自己写公式。

什么时候不用自己算

如果目的只是「这个 IP 是哪里的」,根本不需要转十进制,直接查归属地:IP 地址查询。查到的是机房所在地而不是使用者所在城市,属于正常现象,原因见IP 地址查询显示的位置不对?CDN 节点、AnyCast、IP 库差异与只到城市。

要做的是「网站从哪些地方能不能打开」,用拨测比转换地址更直接:从各地节点发起请求,看的是实际连通结果。

一句话收口:换算本身只有一条公式,容易出错的永远是格式——前导零、点分段、有符号溢出,以及系统解析器和校验器各认一套。

常见问题

192.168.1.1 转成十进制是多少?

3232235777。算法是 192×16777216 + 168×65536 + 1×256 + 1,四段分别乘 256 的三次、二次、一次、零次方再加起来。实测在 IPv4 地址转换器里输入 192.168.1.1,十进制一行显示 3232235777,十六进制 C0A80101。

为什么十六进制结果少几位?1.2.3.4 显示的是 1020304。

因为前导零被省略了,不是算错。1.2.3.4 的十进制是 16909060,十六进制完整应为 01020304,去掉开头的 0 就是 1020304;0.0.0.0 更极端,十六进制只显示一个 0。需要固定 8 位就把结果补到 8 位(padStart(8, "0"))。

二进制那一行为什么是带点的?

工具按四段分别输出 8 位,用点隔开,192.168.1.1 得到 11000000.10101000.00000001.00000001。这种写法和点分十进制一一对应,方便对照;但粘到只认连续 32 位的地方会报格式错,需要去掉点或改用位运算。

能不能输入十进制数字反查 IP?

这个工具不行,它只接受四段点分十进制。实测输入 3232235777,页面红字提示「IPv4 地址格式不正确」,五行结果全部变成「请输入合法的 IPv4 地址」。反查要自己算:一直除以 256 取余,3232235777 除四次得到 192、168、1、1。

为什么 010.1.1.1 工具说格式不对,系统却能解析?

工具要求每段是标准十进制,前导零直接拒。但 glibc 的解析器把前导零当八进制:本机实测 dns.lookup("010.1.1.1") 返回 8.1.1.1。同样,纯数字 3232235777 被解析成 192.168.1.1、2130706433 被解析成 127.0.0.1。拦 SSRF 时只在字符串上比对 127.0.0.1 是不够的。

数据库里 IP 该存整数还是字符串?

要排序、按网段查范围就存整数:字符串排序会把 10.0.0.1 排在 9.0.0.1 前面,整数没有这个问题,而且固定 4 字节、索引更小。注意用无符号:192.168.1.1 的 3232235777 按 32 位有符号存会变成 -1062731519,MySQL 要用 INT UNSIGNED(上限 4294967295)或 BIGINT,也可以直接用 INET_ATON()/INET_NTOA() 换算。

IPv4 地址转换IP 转十进制ip2long点分十进制IP 存储宝塔拨测