核心内容摘要
DeepSeek-R1一周年回顾与MODEL1新模型技术前瞻
// 压缩的BCD码 如 十进制123 对应 0x0123voidLongByteToBCD1(UINT8 longByte,UINT8*a){UINT16 bcd;bcd((longByte/
100)
(((longByte%
/
10)
(longByte%
;*a(UINT
(bcd
;*(a
(UINT
bcd;}UINT16BCDToLongByte(UINT16 bcd){return((bcd
*100(((bcd%
256)
*
(bcd%256%
);}BCD码的概念BCD码是Binary-Coded Decimal的缩写直译是二进制编码的十进制数核心本质是用一组二进制数来表示单个十进制数字0~9是专门为解决「计算机二进制存储」和「人类十进制使用」的衔接问题设计的编码方式也是嵌入式开发、数字电路、仪器仪表中最常用的编码之一之前看到的函数就是嵌入式里BCD码的典型应用。
为什么需要BCD码计算机底层只能存储和运算二进制数但人类日常使用十进制二者直接转换会有问题普通二进制转十进制如0b101010是权值转换适合数值计算但如果是直接显示/传输十进制数字如数码管、液晶屏、串口传数字需要频繁做进制转换效率低硬件外设如数码管、BCD码计数器、实时时钟RTC本身只识别BCD码直接用BCD码存储数字能跳过进制转换直接对接硬件。
简单说BCD码不是为了计算机“计算”而是为了计算机“和人类/硬件交互十进制数字”。
BCD码的核心规则最基础的BCD码是8421-BCD码也是最常用的无特殊说明时BCD码均指它规则极其简单用4位二进制数表示1位十进制数字0~94位二进制的权值依次是
8、
4、
1因此叫8421码按普通二进制计算即可得到对应十进制数4位二进制的取值范围仅用00001001**10101111对应十进制10~15是无效BCD码**绝对不会使用。
基础BCD码编码表0~9这是8421-BCD码的核心对应关系记下来就能直接用嵌入式开发中会频繁接触十进制数字4位8421-BCD码十六进制表示方便书写000000x0100010x1200100x2300110x3401000x4501010x5601100x6701110x7810000x8910010x9关键提醒4位BCD码**没有1015的对应值**比如0b10100xA不是合法的BCD码在BCD码运算/存储中出现这个值就是错误的比如你之前的函数输入最大255拆分后十位、个位都是09刚好符合BCD码规则。
BCD码的两种常用形式重点和你之前的代码强相关计算机的基本存储单位是字节8位而BCD码基础单位是4位因此衍生出非压缩BCD码和压缩BCD码两种形式其中压缩BCD码是你之前函数的核心必须重点理解。
非压缩BCD码也叫无符号BCD码规则1个字节8位存储1位十进制数字其中低4位是有效BCD码0000~1001高4位补0特点存储效率低但处理简单适合表示单个十进制数字或位数少且需要单独操作的数字例子十进制5→ 非压缩BCD码0000 01010x05十进制9→0000 10010x09。
压缩BCD码你之前代码的核心规则1个字节8位存储2位十进制数字其中高4位表示十位的BCD码低4位表示个位的BCD码特点存储效率高是嵌入式开发中表示**两位十进制数00~99**的标准方式也是数码管、RTC时钟的常用格式核心例子和你之前的函数完全对应十进制23→ 十位20010 个位30011→ 压缩BCD码0010 00110x23十进制55→ 十位50101 个位50101→ 压缩BCD码0101 01010x55十进制08→ 十位00000 个位81000→ 压缩BCD码0000 10000x08。
多位十进制数的BCD码表示结合你之前的函数你之前的函数处理的是0~255的三位十进制数核心是把三位十进制数拆成「百位」「十位个位」分别用「非压缩BCD码」「压缩BCD码」存储这是嵌入式中三位十进制数的标准BCD码表示方式举两个核心例子和函数逻辑完全一致例子1十进制123函数输入longByte123拆分百位
十位
个位3百位1用1个字节非压缩BCD码→0000 00010x01十位个位23用1个字节压缩BCD码→0010 00110x23最终BCD码存储0x010x23就是函数中a[0]0x01a[1]0x23的结果。
例子2十进制255UINT8最大值函数输入longByte255拆分百位
十位
个位5百位2非压缩BCD码0000 00100x02十位个位55压缩BCD码0101 01010x55最终BCD码存储0x020x55和之前函数的计算结果完全一致。
例子3十进制5个位数函数输入longByte5拆分百位