其他分享
首页 > 其他分享> > 数据类型-进制转换、整型实型存储

数据类型-进制转换、整型实型存储

作者:互联网

前言

  我们平时使用的数字都是由 0~9 共十个数字组成的,很明显一个数字最多能表示九,如果要表示十以上的数字,就需要多个数字组合起来。
  因为'逢十进一'或称为'满十进一',也因为只有 0~9 共十个数字,所以叫做十进制(Decimalism)。十进制是在人类社会发展过程中自然形成的,它符合人们的思维习惯,例如人类有十根手指,也有十根脚趾。
  进制也就是进位制。进行加法运算时逢X进一(满X进一),进行减法运算时借一当X,这就是X进制,这种进制也就包含X个数字,基数为X。十进制有 0~9 共10个数字,基数为10,在加减法运算中,逢十进一,借一当十。
  与人类社会对应的,计算机基于逻辑运算而诞生,其理论基础建立在布尔代数之上,也因此具有二值逻辑,这又和二进制0/1相对应,因此,二进制符合计算机的思维习惯。因此,计算机内部都是以二进制二进行存储和运算的。由此,如果想要更深研究计算机,掌握二进制及其相应的转换关系至关重要。
  为了满足计算机使用的需要,我们经常使用的有二进制、八进制、十六进制。
  为此,我们有下表:

计数制 二进制 八进制 十进制 十六进制
符号表示 B O D H
进位规则 逢二进一 逢八进一 逢十进一 逢十六进一
基数 2 8 10 16
数码 0,1 0~7 0~9 0~9 , A~F
位权 2x 8x 10x 16x

进制转换

首先我们先了解一下位权的概念:
假设当前数字是 N 进制,那么:
  对于整数部分,从右往左看,第 i 位的位权等于\(N^{i-1}\)
  对于小数部分,恰好相反,要从左往右看,第 j 位的位权为\(N^{-j}\)。
更加通俗的理解是,假设一个多位数(由多个数字组成的数)某位上的数字是 1,那么它所表示的数值大小就是该位的位权。

二进制转换为其他进制

二->十

  先看一个例子:
    \(10010.11_{2}\)=\(1\times 2^{4}+0\times 2^{3}+0\times 2^{2}+1\times 2^{1}+1\times 2^{-1}+1\times 2^{-2}=18.75_{10}\)
  由此,我们注意到我们用当前位的数值乘以当前位的权重,最互相加就可以实现转换,事实也的确如此。

二->八

  二进制与八进制之间存在天然的指数关系,即\(2^{3}=8\),由此,我们可以想到,我们可以把三位二进制数当做八进制的一位进行转换。
  例如:\(100111.01101_{(2)}=47.32_{(8)}\)
  整数部分从右向左划分,小数部分从左向右划分,即100/111/./011/010/计算一下很容易的到的47.32的结果。
  由此,我们总结出二进制到八进制的转换遵循'三位一体'的法则。当然,如果整数部分最右边不够3位,我们在右边补零,同样的,如果小数部分左边不足3位,我们在最左边补零。

二->十六

  就像八进制一样,十六进制是\(2^{4}\),由此,我们可以猜测二进制转换十六进制是不是遵循'四位一体'的法则呢?我们不妨试验一下。
  例如:\(100111.01101_{(2)}=27.68_{(16)}\)
    我们按照八进制的方法给他划分一下0010/0111/.0110/1000/很容易发现这样的转换是正确的。
  由此,我们得到结论,二进制到十六进制的转换遵循'四位一体'的转换法则。和二进制到八进制一样,如果整数部分最右边不够4位,我们在右边补零,同样的,如果小数部分左边不足4位,我们在最左边补零。

八进制转换为其他进制

八->十

  八进制转换为十进制遵循值权相乘累加原则,我们不在赘述,在这里举一个例子验证。
  例如:\(1270_{(8)}=696_{(10)}\)
    \(1\times 8^{3}+2\times 8^{2}+7\times 8^{1}+0\times 8^{0}=696\)

八->二

  诚然二进制到八进制是三位当成一位,那么八进制到二进制就是一位拆分成三位,简单来说就是二进制到八进制转换的逆运算。
  例如:\(521_{(8)}=101/010/001=101010001_{(2)}\)

八->十六

  由于八到十六没有相应的转换规则,通常我们是通过二进制建立两者的联系的,即先把八进制转换成二进制,在把二进制转换成为十六进制。
  例如:\(5361_{(8)}=101/011/110/001_{(2)}=1010/1111/0001=A/F/1=AF1_{(16)}\)

十六进制转换为其他进制

十六进制转换为十进制

  十六进制转换为十进制的方法同样按照位权与数码相乘在依次相加的方式进行。
  例如:\(13FB_{(16)}=5115_{(10)}\)
  即\(13FB_{16}=1\times 16^{3}+3\times 16^{2}+F\times 16^{1}+B\times 16^{0}=5115_{(10)}\)

十六进制转换为二进制

  按照上述叙述,那么十六进制转换为二进制就应该是二进制转换为十六进制的逆运算,那么我们可以把一位十六进制数字差拆分成4位二进制数字。
举一个栗子:\(FB1A4_{(16)}=1111/1011/0001/1010/0100_{(2)}=11111011000110100100_{(2)}\)

十进制与二进制转换

  当然,上述的转换方法是我们必须了解的,但是在计算机中,最常用的是十进制与二进制之间的相互转换,我们在这里单独探讨一下。转换分为整数部分与小数部分。
  针对十进制到二进制我们有如下规则:

      整数部分,除基取余,逆序排列//短除法
      小数部分,乘基取整,顺序排列

我们来举几个栗子来验证一下:

42转换为二进制位101010;运算过程符合除基取余,逆序排列的规则。

0.6875转换为二进制为1011,符合乘基取整,顺序排列的规则。

  对于二进制到十进制的转化,上面已经有相应的介绍。

进制转换总结

1)任意进制到10进制:值权相乘累加原则
2)二进制到八进制:三位一体原则
3)二进制到十六进制:四位一体原则
//以上两个原则反过来即为八/十六进制到二进制转换
4)十进制到二进制:
    整数部分,除基取余,逆序排列
    小数部分,乘基取整,顺序排列

整型在计算机中的存储

  在设计计算机系统时,需要解决计算机如何实现加减法的问题。诚然,加法和减法作为计算机中最基本的运算,计算机时时刻刻都离不开它们,为了提高加减法的运算效率,我们设计硬件电路要设计得尽量简单。对于有符号数,内存要区分符号位和数值位,对于人脑来说,很容易辨别,但是对于计算机来说,就要设计专门的电路,这无疑增加了硬件的复杂性,增加了计算的时间。要是能把符号位和数值位等同起来,让它们一起参与运算,不再加以区分,这样硬件电路就变得简单了。我们发现加法和减法都可以当做加法运算,因为减去一个数相当于加上这个数的相反数,例如,\(5 - 3\) 等价于\(5 + (-3)\),\(10 - (-9)\)等价于 \(10 + 9\)。如果能够实现上面的两个目标,那么只要设计一种简单的、不用区分符号位和数值位的加法电路,就能同时实现加法和减法运算,并且非常高效。实际上,这两个目标都已经实现了,真正的计算机硬件电路就是如此简单。

首先,我们需要普及几个概念:

     1)原码:原码是计算机数据存储方式之一,其表示形式为数值用绝对值表示,在数值的最高位用'0'或者'1'表示正负。
        通俗的理解,原码就是一个整数本来的二进制形式。
     2)反码:对于正数,它的反码就是其原码(原码和反码相同);负数的反码是将原码中除符号位以外的所有位(数值位)取反,也就是 0 变成 1,1 变成 0。
     3)补码:对于正数,它的补码就是其原码(原码、反码、补码都相同);负数的补码是其反码加 1。
        可以认为,补码是在反码的基础上打了一个补丁,进行了一下修正,所以叫“补码”。

  在计算机内存中,整数一律采用补码的形式来存储。这意味着,当读取整数时还要采用逆向的转换,也就是将补码转换为原码。将补码转换为原码也很简单:先减去 1,再将数值位取反即可。
  在这里补充一个原码到反码之间转换的一个简单方法:如果原码为负数,找到原码中倒数第一个为1的数,从这里到后面的不变,前面的翻转(不包括符号位)
  例如:\(100111->111001\),\(1001000->1111000\)
  
  补码完美契合了计算机计算的规律,既简化了硬件设计,有提高了运算顺序,被称之为堪称天才般的设计。

小数在计算机中的存储

  我们常说浮点数,浮点数,那么浮点数是如何在计算机进行存储的呢?
  小数在内存中是以浮点数的形式存储的。浮点数并不是一种数值分类,它和整数、小数、实数等不是一个层面的概念。浮点数是数字(或者说数值)在内存中的一种存储格式,它和定点数是相对的。C语言使用定点数格式来存储 short、int、long 类型的整数,使用浮点数格式来存储 float、double 类型的小数。整数和小数在内存中的存储格式不一样。在C语言中,通常认为浮点数和小数是等价的,并没有严格区分它们的概念,原因是浮点数和小数是绑定在一起的,只有小数才使用浮点格式来存储。其实,整数和小数可以都使用定点格式来存储,也可以都使用浮点格式来存储,但实际情况却是,C语言使用定点格式存储整数,使用浮点格式存储小数,这是在“数值范围”和“数值精度”两项重要指标之间追求平衡的结果。
  首先,我们先声明一下什么是定点数:
  所谓定点数,就是指小数点的位置是固定的,不会向前或者向后移动。
  用定点格式来存储小数,优点是精度高,因为所有的位都用来存储有效数字了,缺点是取值范围太小,不能表示很大或者很小的数字。
由于定点数存在的这种缺点,我们对其进行优化,得到了浮点数(以指数的形式来存储小数的解决方案就叫做浮点数),浮点数是对定点数的升级和优化,克服了定点数取值范围太小的缺点。

以32位浮点数为例(32bit):

符号位 阶码 精度 基数
1bit 8bit 23bit
S E M base

所以,这个浮点数表示的数值为:\(flt = (-1)^{S}×base^{e}×1.M\)
这里,我们需要引入两个概念,阶码的隐式表达,以及归一法
简单来说,浮点数的阶码是一个移位码,移位127位。所以,我们有如下关系:
\(E=e+127\)
移项得到:
\(e=E-127\)
所以实际的指数为E-127;
所谓归一法:就是小数点前的第一位一般情况下为1.

我们举一下栗子(16.625):

      1)当 base 取值为 10 时,19.625 的浮点形式为:
      $19.625 = 1.9625 × 10^{1}$
      2)当 base 取值为 2 时,将 19.625 转换成二进制为 10011.101,用浮点形式来表示为:
      19.625 = 10011.101 = 1.0011101×2^{4}
      由此我们得到,将小数转换成浮点格式后,小数点的位置发生了浮动(移动),并且浮动的位数和方向由 e 决定,所以我们将这种表示小数的方式称为浮点数。

这就是获得图灵奖的IEEE 754标准。
至于关于IEEE 754标准的特殊格式,我们不在此深入讲解。

标签:十六进制,转换,二进制,浮点数,数据类型,实型,整型,八进制,小数
来源: https://www.cnblogs.com/EXQSLoveForever/p/14182681.html