学习途中遇到了很多想不通的地方,花了很多天才明白。
现在记录在学习途中对某些我认为比较难理解的内容进行进一步的解释,希望能加快理解的速度。
以CRC16-CCITT(1021)为例,提供JAVA版的 CRC bit生成与CRC 表的生成与查表的原理。
整个程序:
crc16:
从上面的程序中( value = ((value << 1) + b) ^ 0x1021; )可以看出为什么简记1021。
表的生成原理:将低位统一认为是0,高位的值为索引,余数存储表中.
资料上都是个这样的公式: a ^ b ^ c = a ^ ( b ^ c ) .
可以理解成这样(16位):
11001100 11001100 ^ 0x1021
=
11001100 00000000 ^ 00000000 11001100 ^ 0x1021
这样就可以以字节为单位,拿高位出来跟多项式做异或求得余数保存到表中。
程序:createTable()以字节为单位创建的crc16表。
例子: 11001100 11001100 ^ 0x1021 (已经生成一张存储着0-255的表 table)
= 11001100 00000000 ^ 0x1021 ^ 00000000 11001100
= table[11001100] ^ 00000000 11001100 s
查表法的原理: 当前余数的低位加上当前字节,异或上次的余数。
很绕口,我当初就是载在这了,看了几天都不明白。
程序:getCrc()就是查表的实现。
例子: 00000001 00000002 00000003 ^ 0x1021; crc = 0;
数据扩充16位(crc16) 00000001 00000002 00000003 00000000 00000000 ^ 0x1021;
第一步执行完后 00000000 ^ 00000001 ^ tsable[00000000]; 得余数crc = 00000001;
第二步执行完后 00000001 00000000(左移后) ^ 00000002 ^ table[00000000]; 得余数crc = 00000001 00000002
第三步执行完后 00000002 00000000 ^ 00000003 ^ table[00000001] 得余数 crc = 00000002 00000003 ^ table[1]
最后得余数 24881