数据的表示和运算
考点定位
- 大纲章节:数制与编码、定点数表示与运算、浮点数表示与运算(IEEE 754)、算术逻辑单元
- 常见题型:选择题密集(进制/校验码/范围/溢出/IEEE 754 互转),大题热点是 IEEE 754 表示与浮点运算流程
- 考查频率:高(408 计组部分最高频的章节之一,几乎每年 4-6 分)
- 工程师读者注意:你天天用补码和 float,但考试考手算全流程与教材口径的术语(左规/右规/对阶/溢出判断),坑全在细节
一、进制转换与编码
1.1 进制转换
整数部分除 2 取余(倒序),小数部分乘 2 取整(顺序)。工程师对整数转换无压力,重点是小数的精度陷阱。
小数转换的精度陷阱:多数十进制小数无法精确表示为有限位二进制。
例:(取 1)(取 0)(取 0)(取 1) 回到 ,开始循环:,是无限循环小数。
选择题问法:"十进制 0.6 用二进制表示时是……"答:无限循环小数,无法精确表示。能精确表示的十进制小数分母须为 2 的幂(如 0.5、0.75、0.0625)。
转换链套路:十进制 ↔ 二进制 ↔ 十六进制。八进制/十六进制与二进制按 3 位/4 位一组直转, 位十六进制对应 位二进制。
1.2 BCD 码(8421 码)
每 4 位二进制表示 1 位十进制数字。十进制 59 → 0101 1001。
加法修正规则:两位 BCD 相加若某组结果 > 1001(即 > 9)或产生进位,则该组 +0110(+6)修正。
例:BCD 计算 :,低 4 位为 0001 且有进位,需修正:,即 0001 0111 = 17。
陷阱:BCD 码中 1010~ 1111 六种组合非法;"8421 码是有权码、余 3 码是无权码"是常考对比。
1.3 字符编码(ASCII)与校验位
- 7 位编码共 128 字符;数字 '0' = 30H,大写 'A' = 41H,小写 'a' = 61H(大小写相差 20H,即第 5 位不同)。
- 数字字符的 ASCII 低 4 位即该数字的 BCD 码('5' = 35H)。
校验位计算:如 'A' = 1000001(7 位,含两个 1),配奇校验(使整个码字中 1 的个数为奇数)时校验位 = 1;配偶校验时校验位 = 0。考法常给一个字符让你算奇/偶校验位,或给含校验位的码判断是否出错。
二、校验码
2.1 奇偶校验
- 添加 1 位使码字中 1 的个数为奇(奇校验)或偶(偶校验)。
- 能力:检测 1 位(奇数位)错,不能纠错,不能检测偶数位错。
- 码距(汉明距离)为 2。
2.2 码距与检错纠错能力(必背结论)
设码距为 :
- 检测 位错:
- 纠正 位错:
- 同时检 纠 ():
典型:纠 1 位错需码距至少 3;检 2 位错需码距至少 3;检 1 纠 1 需码距至少 4?——注意口径:只纠 1 位错是 ;"同时检 2 并纠 1"需 。题目常在 3 和 4 之间挖坑,看清楚问的是"仅纠 1"还是"又检又纠"。
2.3 海明码(汉明码)
校验位位数确定:信息位 位,校验位 位,须满足
速查:();();。
分组规则:校验位放在 号位置(第 1、2、4、8…位),第 号信息位由其二进制展开中含 的那些校验位覆盖(第 3 位 = 1+2,被 覆盖;第 5 位 = 1+4;第 6 位 = 2+4;第 7 位 = 1+2+4)。
分步演示【待动画化】:信息位 1010,按偶校验海明编码,,码字 7 位:
- 布局:位置 3、5、6、7 放信息位(按约定次序)
- 求 (覆盖 1、3、5、7 位):
- 求 (覆盖 2、3、6、7 位):
- 求 (覆盖 4、5、6、7 位):
- 码字(第 1→7 位):
纠错演示【待动画化】:接收方收到 (第 5 位 0→1 出错):
- 第 1,3,5,7 位异或
- 第 2,3,6,7 位异或
- 第 4,5,6,7 位异或
- 伴随式 ,第 5 位出错,取反即纠正
能力结论:纠 1 位错或检(不纠)2 位错,标准海明码码距为 3;增设总体校验位后可"检 2 纠 1"( SEC-DED ,实际内存 ECC 的做法)。
2.4 循环冗余校验(CRC)
发送方:信息位左移 位( = 生成多项式最高次数,即除数位数减 1),用模 2 除法(异或,不借位)除以生成多项式对应位串,余数即 FCS,拼接在信息位后。接收方用同一多项式除整个码字,余数非 0 即出错。
模 2 除法分步演示【待动画化】:信息位 1010,生成多项式 ,对应除数 1011,:
被除数 = 1010 后补 3 个 0 = 1010000。
余数 = 011,即 FCS。发送码字 = 1010 011。自检:1010011 ÷ 1011 余 0。
注意:模 2 除法每一位运算都是异或、不进位不借位;"当前窗口最高位是 0 就商 0、异或全 0"这一步最容易漏做导致错位。
三、定点数的表示
3.1 四种机器码对比(含 1 位符号、 位数值,以 8 位整数为例)
一般化(整数,1 符号 + 数值):原码/反码 ;补码/移码 。
必背结论:
- 补码与移码数值位完全相同,仅符号位相反: 符号位取反。如 :,(8 位,偏置 ,)。
- 由 快速求 :连同符号位一起取反加 1。
- 补码算术右移:符号位不变,数值位右移(相当于除以 2 向负无穷取整,)。
- 真值 x 与补码的互推:负数 ,考场速算用"取反加一加负号"。
3.2 补码加减与溢出判断
补码加法:符号位一起参与运算;减法转加法:。
溢出判断三种方法(只有同号相加才可能溢出,异号相加必不溢出):
- 单符号位进位异或:溢出 = 符号位产生的进位 ⊕ 最高数值位向符号位的进位 。两者不同则溢出。
- 双符号位(变形补码):用两位符号位运算,结果符号位 00 正确(正)、11 正确(负)、01 正溢出、10 负溢出(第一符号位永远是正确符号)。
- 操作数与结果符号:同号操作数相加结果符号相反则溢出。
分步演示:8 位补码 :
- ,(均为正数)
- 相加:
- 结果符号位为 1 而操作数均为正 → 正溢出(真值 128 超出 )
- 双符号位验算:,符号 01 → 正溢出,一致
负溢出示例::,相加 ,丢进位得 ,两负得正 → 负溢出;双符号位:,符号 10 → 负溢出。
快速判断技巧:先估算真值是否落在表示范围内,再套公式验证——比纯位级判断更稳。
3.3 乘除(了解即可)
原码一位乘、补码一位乘(Booth)、除法(恢复余数/加减交替)近年以选择考概念(部分积、符号处理)为主,大题概率低,掌握"Booth 算法根据相邻两位判断加减"即可。
3.4 符号扩展与位截断(选择题高频)
- 原码扩展:符号位不动,数值位高位补 0。
- 补码扩展:高位补符号位(正数补 0、负数补 1),值不变。速记:补码的"1 前缀"对负数是无数个符号位,截多长都不变值。
- 截断(长 → 短):直接丢弃高位、保留低位,剩余位按新类型重新解释,值通常改变。
例:8 位 (真值 )扩展为 16 位:(= FFE2H,真值仍为 :)。
考法:给 8 位补码问 16 位扩展后的十六进制;或问",将其作为 16 位数的低 8 位并符号扩展,高 8 位是多少"(92H 最高位 1 → 高 8 位 FFH)。
四、浮点数与 IEEE 754
4.1 格式(必背)
位排列(单精度):
规格化数的真值:
注意 的"1"是隐含位,不占存储,这是 IEEE 754 多一位精度的来源。
4.2 特殊值(必背,选择题高频)
单精度规格化数范围:。阶码真值范围 (全 0、全 1 被特殊值占用)。
4.3 十进制 → IEEE 754 全流程【待动画化】
例:将 转为单精度十六进制。
- 整数/小数分开转二进制:;( 取 1, 取 1);故
- 规格化:,得 ,尾数(去隐含 1)
- 算阶码:
- 拼位:(尾数右补 0 至 23 位)
- 转十六进制:按 4 位分组
反向:0x41C80000 = ?
- 展开二进制:
- 拆分:;;
- 阶码真值 ;尾数
4.4 浮点四则运算流程(大题模板)
加/减五步:对阶 → 尾数运算 → 规格化 → 舍入 → 判溢出。
- 对阶:小阶向大阶看齐,阶小的尾数右移(每移 1 位阶加 1)。为什么不能大阶向小阶?——尾数左移会丢失高位有效数字,右移只丢低位,损失更小。
- 尾数运算:按补码(或教材口径的原码/补码体系)加减。
- 规格化:
- 右规:尾数溢出(如出现 或双符号位异常,)时尾数右移 1 位、阶加 1。右规可能引发阶码上溢。
- 左规:尾数非规格化(补码下符号位与最高数值位相同,即形如 或 )时尾数左移、阶减 1,直到规格化。左规可能引发阶码下溢(下溢一般按机器零处理,不算严重错误)。
- 舍入:右移丢位时处理精度。IEEE 754 默认就近舍入(向偶数舍入, round to nearest even ):丢位后若超出半程则进位,恰为半程(丢弃部分 = 100…0)则使尾数最低位凑成偶数;另有朝 、朝 、朝 0(截断)三种定向舍入。
- 判溢出:溢出的判定只看阶码是否溢出,尾数溢出不算真溢出(可通过右规挽救)。阶码上溢 → 异常/无穷;下溢 → 按机器零。
乘除:阶码相加/相减(减去偏置修正——两数偏置加了两次,单精度须再减 127),尾数相乘/相除,其余步骤同上。
对阶计算示例:,,求 (阶码 3 位含符号口径):
- 对阶: 阶小, 尾数右移 2 位:(01 丢弃,此处先不精究舍入)
- 尾数相加:
- 结果 已规格化,无溢出
五、C 语言中的数据类型转换(真题高频)
工程师天天写隐式转换,考试考的是位级口径——位模式变不变、值怎么变:
- 有符号 ↔ 无符号:
(unsigned)(-1)= FFFFFFFFH = 4294967295。比较运算中有一方是无符号数,另一方也被转为无符号解释:int i=-1; unsigned u=1;则i < u为假。 - int → float:float 尾数有效位仅 24(隐含 1 + 23),而 int 有 31 个数值位, 的整数不能全部精确表示;int → double(53 位有效)总能精确。
- float/double → int:小数部分截断(向零舍入),、;超出 int 范围时结果无意义(超界)。
- char 的符号性:C 标准未定义,408 教材口径按补码(有符号)处理。
典型判断:float f = 16777217;()实际存储值为 ( 恰在 与 中点,向偶数舍入取 ),故 f == 16777216 为真。
例题
例题 1(模拟题) 求信息位 8 位的海明码所需校验位数。
解:: 时 不成立; 时 成立。答案 4。
例题 2(模拟题) 信息位 1100,生成多项式 (1011),求 CRC 码字。
解:被除数 1100000。模 2 除:1100 ⊕ 1011 = 0111,落下 0 得 1110;1110 ⊕ 1011 = 0101,落下 0 得 1010;1010 ⊕ 1011 = 0001,落下 0 得 0010(最高位 0,商 0)。余数 010,码字 = 1100 010。自检:1100010 ÷ 1011 余 0。
例题 3(模拟题) 8 位补码 80H、FFH 分别表示的真值?
解:80H = 1000 0000,符号位 1、数值位取反加一 = ,故真值 (最小负数,唯一没有对应正数的补码);FFH = 1111 1111 → 取反加一 = 1,真值 。
例题 4(模拟题) 判断 8 位补码运算 是否溢出并说明方法。
解:见 3.2 分步演示,正溢出;双符号位结果 01(正溢出),单符号位进位异或 也判定溢出,两种方法一致。
例题 5(模拟题) 将 转为 IEEE 754 单精度十六进制,并反向验证。
解:见 4.3 反向示例,。
例题 6(模拟题) float 变量能否精确存储 ?能否精确存储 ?
解: 的二进制为无限循环(),不能精确;,分母是 2 的幂,能精确(,即 0x3E800000)。
例题 7(模拟题) int i = -1; unsigned u = 1; 判断 i < u 的结果并解释。
解:为假。i 被提升为无符号解释,FFFFFFFH = 4294967295 > 1。位模式一字未改,只是"贴的标签"变了——这正是本章"表示"与"值"分离的核心。
例题 8(模拟题) 8 位补码 92H 符号扩展为 16 位,结果的十六进制是多少?
解:92H = 1001 0010,最高位(符号位)为 1,是负数,扩展时高位补 1:高 8 位 FFH,结果 FF92H(真值 ;验证:92H 无符号值 146, ✓)。
常见坑
- 对阶方向:小阶向大阶(小阶尾数右移)。记忆锚:低个子向高个子看齐,蹲下(右移)比踮脚(左移)安全。
- 右规与左规的时机:尾数绝对值 > 1 → 右规(可能阶上溢);尾数非规格化(符号位与首位数值位相同)→ 左规(可能阶下溢)。考试最爱混着考"尾数溢出 = 浮点溢出"这个错误说法——尾数溢出可右规挽救,阶码溢出才是浮点溢出。
- 双符号位 01 是正溢出、10 是负溢出(不是反的);01/10 里第一位才是真实符号。
- 海明码 别忘"+1";CRC 补 0 个数 = 生成多项式最高次幂(位数减一),不是位数。
- IEEE 754 阶码全 0/全 1 有特殊含义:规格化数阶码真值范围是 ,不是 。
- 移码 = 补码符号位取反,但只适用于同一偏置口径;float 的 E 直接就是移码。
- 8 位补码范围 : 有、 无;问" 再取负"是无解陷阱。
- 奇校验/偶校验 vs 奇偶位数值:偶校验位等于信息位异或(使总数为偶),别记反。
- 有符号与无符号比较:一方无符号则双方按无符号解释,
-1 < 1u为假——工程上未必踩坑(编译器告警),考试专考这一条。 - int → float 可能丢精度(float 只有 24 位有效),int → double 不会(53 > 31);"整型转浮点一定精确"是错误选项常客。
自测
- 十进制 0.625 转二进制小数,结果是什么?
- 信息位 16 位,海明码校验位至少几位?
- CRC 中"模 2 除法"与普通除法的本质区别是什么?
- 8 位机器中, 对应的真值是多少?
- IEEE 754 单精度 0x7F800000 和 0xFFC00000 各代表什么?
- 浮点加减中,什么情况左规、什么情况右规?为什么对阶只能小向大?
- 为什么 int 转 double 不丢精度,转 float 却可能丢?
自测答案与简析
- (1),(0),(1)→ ,可精确表示。
- ,而 时 ,故 5 位。
- 模 2 除法每步做异或、不进位不借位,也不比较大小(首 1 即商 1)。
- (移码 00H = 补码 80H = 真值 −128,移码最小值)。
- 前者阶码全 1、尾数全 0、符号 0 → ;后者阶码全 1、尾数非 0 → NaN(符号位对 NaN 无意义)。
- 尾数溢出(|尾数|>1)右规(尾数右移阶加 1);尾数非规格化左规(尾数左移阶减 1)。大阶向小阶需尾数左移,会丢失高位有效位,故只能小阶向大阶。
- double 尾数有效位 53 位 > int 的 31 个数值位,足以放下;float 只有 24 位有效位, 的整数放不下。