十进制数如何换算成8421BCD码

近日有朋友问起BCD码,在此我们就来说说这BCD码。为什么会有BCD码?由于日常生活中,人们最熟悉的数制是十进制,但计算机内部通常采用2进制和十六进制的形式读写,专业人员理解没问题,但是我们大众要理解2进制,16进制就有些困难了,因此专门规定了一种二进制的十进制码,称为BCD码,它是一种以二进制表示的十进制数码。

二进制编码的十进制数,简称BCD码(Binarycoded Decimal),我们又常叫它8421码,这种方法是用4位二进制码的组合代表十进制数的0,1,2,3,4,5,6 ,7,8,9 十个数符。4位二进制数码有16种组合,原则上可任选其中的10种作为代码,分别代表十进制中的0,1,2,3,4,5,6,7,8,9 这十个数符。最常用的BCD码称为8421BCD码,8.4.2.1 分别是4位二进数的位取值。 十进制数和8421BCD编码和16进制数的对应关系如下:

知道了编码规则,那么将2位BCD码,还原为十进制数就简单了。具体编程函数如下,函数中参数val是一个字节数,那么此BCD码是两位的BCD码,即高四位是一个码值、低四位是一个码值,所以将高四位乘以10加上低四位码值就得到了十进制数。

以上运算后返回的变量i就是十进制数了。

其实在实际运用中,我们也没必要做这样的运算,直接用BCD码的十六进制数就好,比如在时钟芯片DS1302运用中,从DS1302中读取到的时间数据就是BCD码的,那我们现实出来的,人们习惯看到的都是十进制的数,这里我们用个小技巧,大家看上面的编码的对应关系,四位的BCD码,刚好对应一个8位数的十六进制中的四位,比如十六进制0x23,对应的BCD码是0010 0011,也就说十六进制的十位对应一个4位的BCD码,个位又对应一个BCD码,恰巧这个BCD码对应的十进制数就是十六进制的十位和各位,也就说0x23中的2,对应0010,又对应十进制的2,这样一来,我们做显示的时候,直接把十六进制的BCD码除以16,这样就分离出BCD码的十位,余数就是各位,这样显示出来的就是十进制了,其实除以16就是把变量右移4位,在C中右移1位等译除以2,所以除以16就等于右移4位,得到的是高四位,余数自然是低四位,道理和上面的是一样的。例如下面程序:

这里程序中的除以16就是做分离十位和个位用的,其实质就是右移4位取高四位,余数为低四位。

到此,BCD码的转换讲完啦,直接手敲进去的,有错的请大家指出,有不懂的可以加微信:dianzi126,大家一起交流学习。

}

在知乎上上看到以下问题:html

1.该问题出现的缘由 ?java

2.为什么其余编程语言,好比java中可能没有js那么明显python

3.你们在项目中踩过浮点数精度的坑?git

4.最后采用哪些方案规避这个问题的?github

5.为什么采用改方案?chrome

以前本身答的不是满意(对 仍是满意的),想对这个问题作个深刻浅出的总结编程

再看到这几篇长文《》、《》、《》,略有所悟,整理以下:segmentfault

这个问题并不仅是在Javascript中才会出现,任何使用二进制浮点数的编程语言都会有这个问题,只不过在 C++/C#/Java 这些语言中已经封装好了方法来避免精度的问题,而 JavaScript 是一门弱类型的语言,从设计思想上就没有对浮点数有个严格的数据类型,因此精度偏差的问题就显得格外突出。

JavaScript 中的数字类型只有 Number 一种,Number 类型采用 IEEE754 标准中的 “双精度浮点数” 来表示一个数字,不区分整数和浮点数 (js位运算或许是为了提高B格)。

什么是IEEE-745浮点数表示法

IEEE-745浮点数表示法是一种能够精确地表示分数的二进制示法,好比1/2,1/8,1/1024

十进制小数如何表示为转为二进制

即0.25的二进制为 0.01 ( 第一次所获得为最高位,最后一次获得为最低位)

即0.8125的二进制是0.1101(第一次所获得为最高位,最后一次获得为最低位)

因此0.1转化成二进制是:0.01 1001…(无限循环)

同理0.2的二进制是0.11 0011…(无限循环)

IEEE-745浮点数表示法存储结构

在 IEEE754 中,双精度浮点数采用 64 位存储,即 8 个字节表示一个浮点数 。其存储结构以下图所示:

指数位能够经过下面的方法转换为使用的指数值:

IEEE-745浮点数表示法记录数值范围

从存储结构中能够看出, 指数部分的长度是11个二进制,即指数部分能表示的最大值是 2047(2^11-1)

取中间值进行偏移,用来表示负指数,也就是说指数的范围是 [-] 。

所以,这种存储结构可以表示的数值范围为 2^1024 到 2^-1023 ,超出这个范围的数没法表示 。2^1024  和 2^-1023  转换为科学计数法以下所示:

IEEE-745浮点数表示法数值精度

在 64 位的二进制中,符号位决定了一个数的正负,指数部分决定了数值的大小,小数部分决定了数值的精度

IEEE754 规定,有效数字第一位默认老是1 。所以,在表示精度的位数前面,还存在一个 “隐藏位” ,固定为 1 ,但它不保存在 64 位浮点数之中。也就是说,有效数字老是 1.xx...xx 的形式,其中 xx..xx 的部分保存在 64 位浮点数之中,最长为52位 。因此,JavaScript 提供的有效数字最长为 53 个二进制位,其内部实际的表现形式为:

对于超过这个范围的整数,JavaScript 依旧能够进行运算,但却不保证运算结果的精度。

IEEE-745浮点数表示法数值精度丢失

计算机中的数字都是以二进制存储的,二进制浮点数表示法并不能精确的表示相似0.1这样 的简单的数字

若是要计算 0.1 + 0.2 的结果,计算机会先把 0.1 和 0.2 分别转化成二进制,而后相加,最后再把相加获得的结果转为十进制 

但有一些浮点数在转化为二进制时,会出现无限循环 。好比, 十进制的 0.1 转化为二进制,会获得以下结果:

而存储结构中的尾数部分最多只能表示 53 位。为了能表示 0.1,只能模仿十进制进行四舍五入了,但二进制只有 0 和 1 , 因而变为 0 舍 1 入 。 所以,0.1 在计算机里的二进制表示形式以下:

用标准计数法表示以下:

在计算浮点数相加时,须要先进行 “对位”,将较小的指数化为较大的指数,并将小数部分相应右移:

最终,“0.1 + 0.2” 在计算机里的计算过程以下:

通过上面的计算过程,0.1 + 0.2 获得的结果也能够表示为:

经过 JS 将这个二进制结果转化为十进制表示:

这是一个典型的精度丢失案例,从上面的计算过程能够看出,0.1 和 0.2 在转换为二进制时就发生了一次精度丢失,而对于计算后的二进制又有一次精度丢失 。所以,获得的结果是不许确的。

咱们经常使用的分数(特别是在金融的计算方面)都是十进制分数1/10,1/100等。或许之后电路设计或许会支持十进制数字类型以免这些舍入问题。在这以前,你更愿意使用大整数进行重要的金融计算,例如,要使用整数‘分’而不是使用小数‘元’进行货比单位的运算

即在运算前咱们把参加运算的数先升级(10的X的次方)到整数,等运算完后再降级(0.1的X的次方)。

(通常指8421BCD码形式)亦称二进码十进数或二-十进制代码。用4位二进制数来表示1位十进制数中的0~9这10个数。通常用于高精度计算。好比会计制度常常须要对很长的数字串做准确的计算。相对于通常的浮点式记数法,采用BCD码,既可保存数值的精确度,又可免去使电脑做浮点运算时所耗费的时间

  1. 二进制在电路设计中物理上更易实现,由于电子器件大多具备两种稳定状态,好比晶体管的导通和截止,电压的高和低,磁性的有和无等。而找到一个具备十个稳定状态的电子器件是很困难的。

  2. 二进制规则简单,十进制有55种求和与求积的运算规则,二进制仅有各有3种,这样能够简化运算器等物理器件的设计。另外,计算机的部件状态少,能够加强整个系统的稳定性。

  3. 与逻辑量相吻合。二进制数0和1正好与逻辑量“真”和“假”相对应,所以用二进制数表示二值逻辑显得十分天然。

  4. 可靠性高。二进制中只使用0和1两个数字,传输和处理时不易出错,于是能够保障计算机具备很高的可靠性

我以为主要仍是由于第一条。若是好比可以设计出十进制的元器件,那么对于设计其运算器也再也不话下。

JS数字精度丢失的一些典型问题

再问问一个问题 :在js数字类型中浮点数的最高精度多少位小数?(16位 or 17位?……why?

  1. IEEE754 规定,有效数字第一位默认老是1 。所以,在表示精度的位数前面,还存在一个 “隐藏位” ,固定为 1 ,但它不保存在 64 位浮点数之中。也就是说,有效数字老是 1.xx...xx 的形式,其中 xx..xx 的部分保存在 64 位浮点数之中,最长为52位 。因此,JavaScript 提供的有效数字最长为 53 个二进制位

若有不妥之处,请到本人源站留言。不是更新。

}

①设1位十进制数的余3码为ABCD,相应2421码为WXYZ,根据余3码和2421码的编码法则,可作出真值表如表所示。

}

我要回帖

更多关于 十进制转bcd码 的文章

更多推荐

版权声明:文章内容来源于网络,版权归原作者所有,如有侵权请点击这里与我们联系,我们将及时删除。

点击添加站长微信