浮点计数法

2026-09-04

Shuiming: 计算机如何操作浮点数?

Deepseek: 浮点数计数法,本质上就是二进制的科学计数法。它是计算机表示小数(非整数)的标准方式,也是你写的float和double在内存中存储的底层逻辑。


📐 从十进制科学计数法说起

你已经熟悉十进制的科学计数法:

· 123.45 = 1.2345 \times 10^{2} · 0.00123 = 1.23 \times 10^{-3}

它把一个数拆成三部分:

  1. 符号:正或负
  2. 有效数字(尾数):1.2345(在1到10之间)
  3. 指数:2 或 -3

🔢 二进制的科学计数法:浮点数

二进制科学计数法的结构完全相同,只是底数从 10 变成了 2:

\text{数值} = (-1)^{\text{符号}} \times (1.\text{尾数}) \times 2^{\text{指数}}

这个 1.\text{尾数} 的形式,是IEEE 754标准的核心设计:它总是以 1. 开头(对于标准化数),因此这个 1 不需要存储,从而省出1位来提高精度。


🧬 三种精度(你常用的)

类型 总位数 符号位 指数位 尾数位 十进制精度 float(单精度) 32 1 8 23 约7位有效数字 double(双精度) 64 1 11 52 约16位有效数字 long double(扩展) 80或128 1 15 64 约19位有效数字


🛠️ 指数是如何存储的?—— 偏置值(Bias)

指数不直接存储,而是加上一个偏置(Bias),使指数总是非负数,便于比较大小。

· float 偏置 = 127:实际指数范围 -126 ~ +127,存储为 1 ~ 254 · double 偏置 = 1023:实际指数范围 -1022 ~ +1023,存储为 1 ~ 2046

示例:1.0 的指数是 0,在 float 中存储为 0 + 127 = 127(二进制 01111111)。


🧪 实际转换示例:6.625 → 32位 float

  1. 二进制:6.625 = 110.101
  2. 标准化:1.10101 × 2²(尾数部分为 10101)
  3. 指数:2 + 127 = 129 = 10000001
  4. 尾数:10101000000000000000000(23位)
  5. 符号:正,所以为 0

最终32位(十六进制):

0 10000001 10101000000000000000000
= 0x40D40000

⚠️ 精度误差的根源

并非所有十进制小数都能用二进制精确表示。

· 0.1 在二进制中是一个无限循环小数: 0.1 \approx 0.000110011001100110011..._2 · 所以 0.1f 存储的只是它的近似值,这就是为什么 0.1 + 0.2 != 0.3。


🧩 特殊值(IEEE 754标准)

情况 符号 指数 尾数 含义 正零 0 0 0 0.0 负零 1 0 0 -0.0 正无穷 0 全1 0 +∞ 负无穷 1 全1 0 -∞ NaN 0或1 全1 非0 非数字(如 0/0)


🌱 与你的学习路径的关系

你之前已经理解了:

· 二进制与补码(整数) · 位运算与移位 · 所有计算可以简化为基础运算

现在你在补充:

· 小数如何存储 · 为什么会有精度问题 · 如何安全地比较浮点数(使用容差,而不是 ==)


浮点数计数法是C语言中理解数据表示的最后一块拼图。你已经掌握了整数和位运算的底层逻辑,现在正在补充浮点数的部分。 🧘‍♂️💻⚡🔢