3.4 · 二的补码
目标: 把任意整数转成 n 位二的补码形式,再转回去。
负数的问题
二进制只有 0 与 1 —— 没有 − 号。电脑怎么储存负整数?
历史上有三种方案:
| 方案 | 思想 | 缺点 |
|---|---|---|
| Sign-magnitude 符号-绝对值 | 最左位作符号(0 = +,1 = −),其余是绝对值 | 有两个零(+0、−0);减法尴尬 |
| One's complement 一的补码 | 全部位反转表示负 | 仍有两个零;进位处理乱 |
| Two's complement 二的补码 | 全部反转,再加 1 | 单一零;加减统一处理 |
现代电脑全部用二的补码表示有符号整数。HKEAA 明确要求你掌握。
怎么编码一个负整数
3 步配方
要在 n 位二的补码表示 −x:
- 把
+x写成 n 位二进制。 - 每位反转(一的补码)。
- 加 1。
例 · 8 位下的 −5
| 步骤 | 过程 |
|---|---|
| 1. 写 +5 | 0000 0101 |
| 2. 反转 | 1111 1010 |
| 3. 加 1 | 1111 1011 |
所以 −5 = 1111 1011₂ 在 8 位二的补码中。
例 · 8 位下的 −1
| 步骤 | 过程 |
|---|---|
| 1. 写 +1 | 0000 0001 |
| 2. 反转 | 1111 1110 |
| 3. 加 1 | 1111 1111 |
−1 就是全 1。(任何位数皆如此。)
例 · 8 位下的 −128
| 步骤 | 过程 |
|---|---|
| 1. 写 +128 | 1000 0000(已是负数解读,但位模式相同) |
| 2. 反转 | 0111 1111 |
| 3. 加 1 | 1000 0000 |
位模式 1000 0000 在二的补码中表示 −128 —— 8 位有符号最小值。
怎么解码二的补码数字
如果 MSB 为 0 → 是正数;按普通二进制读。
如果 MSB 为 1 → 是负数。两种换算:
方法 1 · 套同样的配方(对称!)
1111 1011₂ → 反转 → 0000 0100 → +1 → 0000 0101 = 5 → 所以原值为 −5。
方法 2 · 用负的 MSB 位值
对 n 位二的补码,MSB 的位值是 −2ⁿ⁻¹ 而不是 +2ⁿ⁻¹。
8 位时:
| 位 | −128 | 64 | 32 | 16 | 8 | 4 | 2 | 1 |
|---|---|---|---|---|---|---|---|---|
| 位元 | 1 | 1 | 1 | 1 | 1 | 0 | 1 | 1 |
值 = −128 + 64 + 32 + 16 + 8 + 0 + 2 + 1 = −5。✓
n 位二的补码范围
| 位数 | 范围 |
|---|---|
| 4 | −8 到 +7 |
| 8 | −128 到 +127 |
| 16 | −32,768 到 +32,767 |
| 32 | −2,147,483,648 到 +2,147,483,647 |
公式:n 位时,范围为 −2ⁿ⁻¹ 到 +2ⁿ⁻¹ − 1。
注意不对称:负值比正值多一个,因为 0 住在正的一侧(0000 0000)。
二的补码为何精彩
零只有一种表示
符号-绝对值有 +0 和 −0。二的补码只有 0000 0000 = 0。
减法即加法
A − B = A + (B 的二的补码)。
同一套电路加正数和负数 —— 不用单独减法器。
符号扩展自然成立
把 8 位有符号数复制到 16 位寄存器,只要把 MSB 复制到新增的上位即可:
8 位 −5 = 1111 1011
16 位 −5 = 1111 1111 1111 10112
实例
例 A · 4 位二的补码下算 7 − 3
+7 = 0111+3 = 0011,所以 −3 = 0011 → 1100 → 1101。
相加:0111 + 1101 = 1 0100。丢弃 MSB 进位 → 0100 = +4。✓
例 B · 8 位二的补码下算 5 − 9
+5 = 0000 0101−9 = 0000 1001 → 1111 0110 → 1111 0111
相加:0000 0101 + 1111 0111 = 1111 1100 = −4。✓
学生常见错误
- 忘了第 3 步(加 1) —— 这就是一的补码与二的补码的差别。
- 把 MSB = 1 当作永远是负 —— 仅在二的补码下成立;无符号二进制里 MSB 只是普通位。
- 范围不对称 bug:试图用 8 位有符号表示 +128(超界)。
- 混宽度 —— 比较 4 位有符号
1011与 8 位有符号1011会得到不同值。
练习活动
在 8 位二的补码下求:
−1的位模式。−42的位模式。1110 0000的十进制值。1000 0000的十进制值。- 可表示值的范围。
答案
1111 11111101 0110(+42 =0010 1010→ 反转1101 0101→ +1 →1101 0110)−32−128−128到+127
考试式题目
题(4 分): 用 8 位二的补码把
−45₁₀表为二进制,写出过程。
参考答案:
| 步骤 | 过程 |
|---|---|
| 1. 写 +45 为 8 位二进制 | 0010 1101 |
| 2. 每位反转 | 1101 0010 |
| 3. 加 1 | 1101 0011 |
−45₁₀ = 1101 0011₂ 在 8 位二的补码中。
关键要点
- 二的补码 = 全部反转,再加 1。
- 二的补码数字的 MSB 位值是
−2ⁿ⁻¹。 - 零只有一种表示。
- 加减法共用硬件。
- 范围:
−2ⁿ⁻¹到+2ⁿ⁻¹ − 1。
➡️ 下一节:3.5 字符编码