计算机中的数制与编码(校验码篇)
简介
- 校验码是指能够发现或者能够自动纠错的数据编码,也称为检错纠错编码。
- 对于某种编码得到的所有二进制数字,两两之间的最少数字变化叫做码距。
- 例如通过某种规则对0,1,2,3四个数字进行编码,结果如下。
- 从中可以看出0和1之间的码距为2(因为只有后两位不同)、0和2之间的码距为2、1和2之间的码距为2、1和3之间的码距为4……那么该编码的码距就是其中最小的2!
数字 | 编码后的结果 |
---|---|
0 | 0000 |
1 | 0011 |
2 | 0110 |
3 | 1100 |
- 对于码距不小于2的数据校验码开始具有了检错能力。码距越大,检错纠错的能力就越强,检错能力(发现出错的能力)永远大于纠错能力(发现是哪一位出错)。
- 由于计算机中只有0和1,因此只要发现某一位出错,将数值取反即可完成修改。
奇偶校验码
实现方式
-
奇校验码:在原编码的首部增加一位,使整个编码中“1”的个数是奇数。
- 例如原编码为 (2)10 = (0010)2,则奇校验码为 (00010)2
-
偶校验码:在原编码的首部增加一位,使整个编码中“1”的个数是偶数。
- 例如原编码为 (2)10 = (0010)2,则奇校验码为 (00010)2
能力评价
- 奇偶校验码只能检测出编码是否发现了奇数个错误,不能检测出偶数个错误。例如:
- 原编码是0001000,对其使用奇校验得到00001000,结果在数据传递过程中数据发生了错误,变成了00001001,接收方发现该数据的“1”的个数是偶数个,不符合奇校验码的特性,故该数据有误。
- 同理,若原数据出错后变成了00111001,也是发生了奇数个(三个)错误,可以被检测出来。
- 然鹅,若原数据变成了00001110,那么该数据是符合奇校验码的特征的,故不会被检测出错误。
- 另外,奇偶校验码只能检错,不能纠错,通常只用于对存储器中的数据进行检查或传输数据的检查。
做个训练(答案见下方参考答案)
- 请你给出10101和01010的奇偶校验码。
- 在某网络中采用偶校验的ASCII码,收到的数据为10101010,则该数据()。
- A.没有错误 B.有错误 C.不能确定
海明码(汉明码)
简单介绍
- 海明码是一种广泛采用的校验码,利用了奇偶校验码的原理,应用海明码能够发现错误,并精准发现错误的位置。
实现原理(本文介绍前向纠错方式,其他方式不予介绍)
确定校验码位数:x+n ≤ 2n-1
- 我们假设原数据有x位,首先我们要确定用于校验位的位数n:
- 因为校验位的位数为n,那么用于校验位就有2n种取值,也就是可以表示数据的2n种状态(数据正确?第一位出错了?第二位出错了?……第2n-1位出错了?)。也就是说,n位校验位只能涵盖2n-1位的总数据。
- 即:总数据位数 = x+n ≤ 2n-1,由此我们可以求出n,显然为了经济实惠,传输的比特数越少越好,故满足条件的最小的n值为所求。
确定校验码插入位置:Ck->总数据第2k位
- 接下来我们要确定校验位插入原数据的位置。
- 将校验位放在2n处,即第1位、第2位、第4位……
- 不妨假设x = 4,原数据为1010,由上一步我们可以求得n = 3。将校验位用C1C2C3表示,则可得到下表:
位置 | 111 | 110 | 101 | 100 | 011 | 010 | 001 |
---|---|---|---|---|---|---|---|
数据 | 1 | 0 | 1 | C3 | 0 | C2 | C1 |
计算校验码的值:异或操作
- 上一步,我们将第k位的校验码Ck放置在数据的第2k位,这一步我们计算第k位的校验码的值
- 找到所有位置编码的第k位等于1的数字异或起来,即可得到第k位校验码Ck的值。
- 例如计算C1就要找到所有位置编码的第一位是1的数字:位置编码011、101、111的数字,下表标黄:
位置 | 111 | 110 | 101 | 100 | 011 | 010 | 001 |
---|---|---|---|---|---|---|---|
数据 | 1 | 0 | 1 | C3 | 0 | C2 | C1 |
- 可以得到C1 = 1⊕1⊕0 = 0
- 同理我们可以得到C2 = 1 ⊕0⊕0 = 1,C3 = 1⊕0⊕1 = 0
- 故整个海明码为1010010
利用海明码检错:还是异或操作
- 假设接收端接收到的数据是1010010,我们怎么知道收到的数据错没错呢?
位置 | 111 | 110 | 101 | 100 | 011 | 010 | 001 |
---|---|---|---|---|---|---|---|
数据 | 1 | 0 | 1 | 0 | 0 | 1 | 0 |
- 我们将所有位置位为k的数字异或起来:
- S1 = 1⊕1⊕0⊕0 = 0(上图标黄)
- S2 = 1⊕0⊕0⊕1 = 0
- S3 = 1⊕0⊕1⊕0 = 0
- 故 S = 000 表示没有发现错误(通常来说),这是显然的,因为1010010就是我们上一步算出来的。当然如果这个数据错得太离谱,海明码也会失效,下面还会提及,不过通常计算中S = 000时就默认没错了。
- 同理,假如接收端接收到的数据有一位出了错误,数据为1010011,经过计算得 S = 001,即第一位出错了。
能力评价
- 那么假如接收端接收到的数据为1010001,经过计算得S = 011,那么是第三位错了吗?不是,因此我们只能遗憾的宣布,海明码只能纠正一位错误。
- 那么假如接收端接收到的数据为1010101,经过计算得S = 000,那么就没问题了?显然也不是,因为我们原数据可是1010010啊,也就是说,海明码最多只能发现两个错误。
- 综上所述,海明码只能检两位错,纠一位错。
奇思妙想
- 我们发现:S=001时,是第一位出了错,这怎么会这么神奇?
- 其实通用的理解是这样的:
位置 | 111 | 110 | 101 | 100 | 011 | 010 | 001 |
---|---|---|---|---|---|---|---|
数据 | a | b | c | d | e | f | g |
- S3 = a⊕b⊕c⊕d = 0 表示abcd中没有错
- S2 = a⊕b⊕e⊕f = 0 表示abef中没有错
- S1 = a⊕c⊕e⊕g = 1 表示aceg中有一个错
- 那么显然就是g错了,了解了通用方法后,海明码怎么变型也不怕啦!
做个训练
- 用海明码来检错,若原信息为10101010,则需要用多少个校验位?
- 海明码可以检测()位错误,纠正()位错误?
A.2,1 B.1,2 C.3,2 D.2,0
CRC码(循环冗余校验码)
基本思想
- 发送端在K位信息码后拼接R位校验码,整个编码长度为N位,故也称(N,K)码
- R位校验码时K位信息码与生成多项式G(x)做模2除法得到的
- 在接收端对整个数据使用G(x)进行模2除法,若能够整除,则说明信息无误。
- 当然,和海明码一样,也是不能错的太离谱了,毕竟检错能力也有限。
基本概念
- 生成多项式G(x):最高幂次为R次方,转换成二进制有R+1位。
- 模2除法:对被除数从左到右每R+1位依次做异或运算,若首位为零则跳过
- 被除数:将信息码用零扩充R位
- CRC码:CRC码 = 原数据 + 余数
基本过程
- 假设原数据为101001,生成多项式G(x)=x3+x2+1,求CRC码。
- 如上图所示,除数为1101,被除数为101001000(即101001扩展了3位),得到的余数为001,故CRC码为101001001。
检错纠错
- 将CRC码对生成多项式进行模2除法,若余数为0,则证明没有发生错误
- 若除数为4位,余数为001,则说明数据发生了错误
做个训练
- (不定项)下列说法正确的是()
A.校验码的码距必须大于2
B.校验码的码距越大,检错纠错能力越强
C.CRC码是通过除法建立数据与校验位的关系的
D.海明码能检测出两位错误,并予以纠正
E.只要增加奇偶校验位的位数,就能提高正确性 - 求11100和11101的CRC校验码,生成多项式G(x)=x^2+x+1
参考答案
奇校验码 | 偶校验码 | |
---|---|---|
10101 | 010101 | 110101 |
01010 | 101010 | 001010 |
- C,可能出现偶数位错误,奇偶校验码只能检测出奇数个错误!
- 4位。原数据8位,8+x≤2x-1,得x≥4
- A
- BC。A项可以等于二;D项只能纠错一位;E项还要考虑码距问题。
- 1110000、1110111