PC_浮点数表示/定点数和浮点数比较/溢出/C语言中的浮点数类型

浮点数

  • 根据小数点的位置是否固定,分为定点数和浮点数

  • 定点数采用不同机器数编码(原码/补码/移码)的情况

    • 定点数

      • 定点补码整数表示整数
    • 浮点数

      • 浮点数不再使用补码来表示,而是用原码和移码组合表示
        • 定点原码小数表示浮点数的尾数(定点小数)
        • 移码表示浮点数阶码部分(移码整数)
    • 参考IEEE 754标准

ref

浮点数表示

  • 浮点数表示法是指以适当的形式将比例因子表示在数据中,让小数点的位置根据需要而浮动。
  • 这样,在位数有限的情况下,既扩大了数的表示范围,又保持了数的有效精度
    • 例如,用定点数表示电子的质量或太阳的质量是非常不方便的。
    • 使用浮点是可以较好表示

浮点数形式分析

  • 一个浮点数可以分为两大部分:阶数;尾数

    • 阶数:{(阶符),(阶码数值)};

      • 阶符
      • 阶码
    • 尾数:{(数符).(数码数值)}

      • 数符
      • 数码
    • 计算机中,基数是默认值为2,不用写出来

书面形式的一般浮点数(真值)

  • 这个部分是以真值的形式讨论(真值的二进制形式)

    • 某些语境下,是以真值的机器码表示的(比如补码/原码/移码)
    • 不同机器编码下得到的规律不一样,不要混淆了,但真值形式是根本
  • 对于r进制的浮点数,可以表示为:

    • N = S × r j N=S\times{r^j} N=S×rj

      • 其 中 其中
        • S 是 尾 数 S是尾数 S(可正可负)
          • 可以采用定点原码小数表示
        • j j j为阶码(指数)(也就是基数r的指数)(可正可负)
          • 可以采用移码整数
        • r r r是基,在计算机中,通常r=2,即二进制(也可以去2的其他幂,比如4,8,…)
  • 在计算机中,为了提高数据的精度,以及便于比较

    • 规定浮点数的尾数纯小数的形式
      • S ∈ [ 0 , 1 ) S\in[0,1) S[0,1)
      • 比 如 1 表 示 为 0.1 × 10 比如1表示为0.1\times{10} 10.1×10
    • 比如 a = 0.11 × 2 10 1 2 a=0.11\times{2^{101_2}} a=0.11×21012
      • b = 0.011 × 2 10 1 2 b=0.011\times{2^{101_2}} b=0.011×21012
      • 可以看到,表示相同值的两个数a,b的尾数部分0.11和0.011占用了不同位数的小数位
      • 为进一步提高精度(在有限的机器字长位数下),一般采用规格化数
        • 将在规格化数部分讨论

小数:纯小数和带小数(混小数)

  • 小数,是实数的一种特殊的表现形式。
    • 所有分数都可以表示成小数,小数中的圆点叫做小数点,它是一个小数的整数部分和小数部分的分界号。
  • 整数部分是零的小数叫做纯小数(pure decimal),
    • 如0.3,0.48,0.999等。
  • 整数部分不为零的小数叫做带小数(mixed decimal)
  • reference link
🎈二进制规格化浮点数
  • 为了进一步规范浮点数(保证尽可能高的精度)提出规格化数(浮点数)

    • 最高位是1的浮点数就是规格话数,例如
      • a = 0.11 × 2 10 1 2 a=0.11\times{2^{101_2}} a=0.11×21012,而b就不是
      • c = 101.11 × 2 10 1 2 c=101.11\times{2^{101_2}} c=101.11×21012这个也不是,因为它位数是纯小数的条件的都不满足
  • 对于基数不同的浮点数,其规格化数的标准有所不同,规格化的过程也有所不同

计算机中的二进制浮点数形式

  • 本节依然是从真值的二进制形式讨论
非标准形式讨论浮点数
  • 通常,机器中的浮点数形如:

    • F = j f j 1 ⋯ j m ⏟ 阶 码 ( 数 值 部 分 ) S f S 1 ⋯ S n ⏟ 尾 数 的 数 值 部 分 F=j_f\underbrace{j_1\cdots{j_m}}_{阶码(数值部分)}S_f\underbrace{S_1\cdots{S_n}}_{尾数的数值部分} F=jf() j1jmSf S1Sn

      • 该形式可以看做两大部分:

        • 阶 码 ( 也 叫 ( 基 的 ) 指 数 ) j = j f j 1 ⋯ j m 阶码(也叫(基的)指数)j=j_fj_1\cdots{j_m} (())j=jfj1jm

          • j f 是 阶 符 j_f是阶符 jf
          • j是整数,反映了浮点数的表示范围小数点的位置
        • 尾数 S = S f S 1 ⋯ S n S=S_fS_1\cdots{S_n} S=SfS1Sn

          • S f S_f Sf是数符
          • S是纯小数,反映了浮点数的精度,位数的符号 S f S_f Sf代表了浮点数的正负
        • 小数点:

          • 尾数是纯小数,其小数点位于 S j S_j Sj S 1 S_1 S1之间
          • 阶码j是定点整数,也有自己的小数点(位于 j m j_m jm S f S_f Sf之间)
            • 但是实际决定F的取值范围的,是阶码整体j
    • 回顾书面形式的浮点数: F = S × r j F=S\times{r^j} F=S×rj

      • S就是尾数
      • j就是阶码
      • 基数r被默认为2
IEEE标准中的结构
  • 和非标准结构大致类似,但是数符 S f S_f Sf被提前了到浮点数结构的第一部分(参看文末部分)

🎈🎈🎈浮点数的表示范围(非规格化时)

  • 设浮点数阶码的数值位取m位,尾数的数值位取n位,当浮点数为非规格化数时,它在数轴上的表示范围:

1646303050232

  • 浮 点 数 = 阶 数 × 尾 数 浮点数=阶数\times 尾数 =×

n位数值位的小数和整数最值

  • 下面的讨论是基于真值(与具体机器数编码相独立)

  • 纯小数:

    • ∣ p ∣ ∈ ( 0 , 1 ) ∣ p ∣ ∈ [ 2 − n , 1 − 2 − n ] − ∣ p ∣ ∈ [ 2 − n − 1 , − 2 − n ] 2 − n = 0. 0 ⋯ 01 ⏟ n − 1 个 0 , 末 尾 1 1 − 2 − n = ( 0. 1 ⋯ 11 ⏟ n 个 1 ) 2 = ∑ i = 1 n 2 − i |p|\in(0,1) \\ |p|\in[2^{-n},1-2^{-n}] \\-|p|\in[2^{-n}-1,-2^{-n}] \\\\ \\2^{-n}=0.\underbrace{0\cdots{01}}_{n-1个0,末尾1} \\1-2^{-n}=(0.\underbrace{1\cdots{11}}_{n个1})_2=\sum\limits_{i=1}^{n}2^{-i} p(0,1)p[2n,12n]p[2n1,2n]2n=0.n10,1 00112n=(0.n1 111)2=i=1n2i

    • 纯小数对应于浮点数的尾数(的数值位部分)

  • 整数:

    • ∣ z ∣ = 0 , 1 , 2 , ⋯   , 2 n − 1 − ∣ z ∣ = 1 − 2 n , ⋯ 0 |z|=0,1,2,\cdots,2^{n}-1 \\ -|z|=1-2^{n},\cdots{0} z=0,1,2,,2n1z=12n,0

    • 对应于浮点数阶码(数值位部分)

  • 设浮点数 F = j f j 1 ⋯ j m S f S 1 ⋯ S n F=j_fj_1\cdots{j_m}S_fS_1\cdots{Sn} F=jfj1jmSfS1Sn

    • 即,阶码数值位部分有m位,尾数数值部分n位

    • 浮点数的取值范围具有对称性

    • 下面仅对正数的一侧做讨论

      • 最小浮点数(浮点数最小绝对值):
        • 注意到,浮点数的正负性是由尾数的数符位 S f S_f Sf决定的

          • 阶码总是正数(尽管阶符可以是负的
            • 指数函数( 2 j 2^{j} 2j总是有大于0的函数值, 2 x 2^x 2x是个递增函数,
            • 所以,当j取得最小值 2 − 1 ⋯ 11 = 2 − ( 2 m − 1 ) 2^{-1\cdots{11}}=2^{-(2^{m}-1)} 2111=2(2m1)
            • 同 时 尾 数 S 取 到 最 小 值 0.0 ⋯ 01 = 2 − n 同时尾数S取到最小值0.0\cdots{01}=2^{-n} S0.001=2n
        • 最小阶码( 2 − ( 2 m − 1 ) 2^{-(2^m-1)} 2(2m1)乘以最小尾数:(最接近0的正浮点数数)

          • J M i n ∣ S ∣ M i n = 2 − ( 2 m − 1 ) 2 − n J_{Min}|S|_{Min}=2^{-(2^{m}-1)}2^{-n} JMinSMin=2(2m1)2n
        • 最 大 阶 码 ( 2 ( + ( 2 m − 1 ) ) ) 乘 以 最 大 尾 数 ( 2 − n − 1 ) 最大阶码(2^{(+(2^m-1))})乘以最大尾数(2^{-n}-1) (2(+(2m1)))(2n1)

          • J M a x ∣ S ∣ M a x = 2 ( 2 m − 1 ) ( 2 − n − 1 ) J_{Max}|S|_{Max}=2^{(2^{m-1})}(2^{-n}-1) JMaxSMax=2(2m1)(2n1)
    • 小结:

      • 以上就是正半轴的情况,负半轴取符号得到对称的边界值
      • 最大负浮点数:(最接近0的负浮点数)
        • − J M i n ∣ S ∣ M i n = − ( 2 − ( 2 m − 1 ) 2 − n ) -J_{Min}|S|_{Min}=-(2^{-(2^{m}-1)}2^{-n}) JMinSMin=(2(2m1)2n)
      • 最小负浮点数:(最远离0的负浮点数)
        • − J M a x ∣ S ∣ M a x = − ( 2 ( 2 m − 1 ) ( 2 − n − 1 ) ) -J_{Max}|S|_{Max}=-(2^{(2^{m-1})}(2^{-n}-1)) JMaxSMax=(2(2m1)(2n1))
    • 特点:

      • 观察上述最值,发现阶码的数值部分绝对值是最大的m位二进制数

        • 🎈以下的0/1串都是真值的二进制形式

        • 2 − 1 ⋯ 11 × 0.0 ⋯ 01 2 + 1 ⋯ 11 × 0.1 ⋯ 01 − 2 − 1 ⋯ 11 × 0.0 ⋯ 01 − 2 + 1 ⋯ 11 × 0.1 ⋯ 01 2^{-1\cdots{11}}\times0.0\cdots{01} \\ 2^{+1\cdots{11}}\times0.1\cdots{01} \\ -2^{-1\cdots{11}}\times0.0\cdots{01} \\ -2^{+1\cdots{11}}\times0.1\cdots{01} 2111×0.0012+111×0.1012111×0.0012+111×0.101

🎈浮点数表示范围和溢出

  • 判断浮点数溢出,是通过比较阶码来进行

  • 上溢:

    • 这个好理解,当浮点数的阶码大于最大阶码时,就是发生上溢,这种情况下机器停止运行,进行中断溢出处理
    • 正上溢负上溢,绝对值都是向无穷大方向发展而发生的
  • 下溢:

    • 当浮点数阶码小于最小阶码时,称为下溢
    • 正下溢负下溢的绝对值都是向0靠近而发生的
    • 注意,浮点数可以取到0
      • 但是,由于精度的限制(尾数位数有限),很接近0但不等于0的数是表示不了的(存在一个类似于盲区的区域)
      • 即,在值落在0的邻域时,可能发生下溢
      • 此时的数绝对值十分小,通常的,将尾数各位强制置为0,按照机器零处理

🎈规格化数

🎈🎃定点数vs浮点数

  • 当浮点机和定点机中的位数相同
    • 范围:浮点数的表示范围比定点数大得多
      • 定点数和浮点数都可以表示
        • 整数
        • 小数
      • 在定点机中,由于小数点位置固定不变,当机器处理的数不是纯小数或者纯整数的时候,需要乘以一个比例因子,否则会产生溢出
      • 采用定点小数的机器称为定点机
        • 数值部分的位数n决定了定点机中数的表示范围
        • 如果机器数采用原码:
          • 小数定点机中的表示范围是 − ( 1 − 2 − n ) ∼ 1 − 2 − n -(1-2^{-n})\sim{1-2^{-n}} (12n)12n(对称)
          • 整数定点机中数的表示范围: − ( 2 n − 1 ) ∼ 2 n − 1 -(2^n-1)\sim{2^n-1} (2n1)2n1
    • 精度:当浮点数是规格化数时,其相对进度也比定点数高得多
      • 这要分情况:比如对于x=0.1001011 101010…,y=0.00000000010110…
        • 对于两台相同字长(8位)的定点机A和浮点机B:
        • x用A表示精度更高
          • 因为x已经是规格化数,定点机的所有bit都可以用来表示尾数的各个位数,可以达到最高精度
        • y用B表示精度更高
          • 前提是y要进行规格化,这样可以将有效位表示到更后面.
    • 运算效率:定点数运算比较快
      • 浮点数运算要分为阶码部分和位数部分的运算
      • 而且运算结果都要规格化,(浮点数的运算步骤比定点数多)
    • 溢出判断:
      • 浮点数的溢出判断是对规格化数的阶码进行判断
      • 定点数是对数值本身进行判断
        • 比如,小数定点机中的数,其绝对值如果大于1,就是溢出
          • 为了避免溢出,处理非纯小数前,需要选择比例因子,比较麻烦
          • 原因是定点数的小数点被规定在符号位之后,且不可移动
        • 浮点数的表示范围大,仅当上溢才会停止运算,一般不考虑比例因子的选择
    • 定点机可以通过软件实现浮点运算或者外加浮点扩展硬件

IEEE 754标准的浮点数格式

S f E S 1 ∼ n 数 符 阶 码 部 分 ( 移 码 整 数 ) 尾 数 数 值 位 ( 用 定 点 原 码 ) S f ( 数 符 )  阶码(含阶符)   尾数  \\ \begin{array}{|l|l|l|} \hline S_f & E & S_{1\sim{n}} \\ \hline 数符&阶码部分(移码整数)&尾数数值位(用定点原码) \\\hline \end{array} \\ \begin{array}{|l|c|c|} \hline S_f(数符) & \text { 阶码(含阶符) } & \text { 尾数 } \\ \hline \end{array} SfE()S1n()Sf() 阶码(含阶符 尾数 

  •  符号位  S  阶码   尾数   总位数   短实数  1 8 23 32  长实数  1 11 52 64  临时实数  1 15 64 80 \begin{array}{lcccc} & \text { 符号位 } S & \text { 阶码 } & \text { 尾数 } & \text { 总位数 } \\ \text { 短实数 } & 1 & 8 & 23 & 32 \\ \text { 长实数 } & 1 & 11 & 52 & 64 \\ \text { 临时实数 } & 1 & 15 & 64 & 80 \end{array}  短实数  长实数  临时实数  符号位 S111 阶码 81115 尾数 235264 总位数 326480

  • 其中,S为数符,它表示浮点数的正负,但与其有效位(尾数)是分开的。

  • 阶码用移码表示,阶码的真值都被加上一个常数(偏移量),

  • 如短实数,长实数和临时实数的偏移量用十六进制数表示分别为7FH,3FFH和3FFFH。
  • 尾数部分通常都是规格化表示,即非“O”的有效位最高位总是“1”,但在IEEE标准中,有效位呈如下形式。
    1▲ffff……-fff
    其中▲表示假想的二进制小数点。
  • 在实际表示中,对短实数和长实数,这个整数位的1省略,称隐藏位;
  • 对于临时实数不采用隐藏位方案

表格

NameCommon nameBaseSignificand bits[b] or digitsDecimal digitsExponent bitsDecimal E maxExponent bias[14]E minE maxNotes
binary16Half precision2113.3154.51 2 4 − 1 = 15 2^4−1 = 15 241=15−14+15not basic
binary32Single precision2247.22838.23 2 7 − 1 = 127 2^7−1 = 127 271=127−126+127
binary64Double precision25315.9511307.95 2 10 2^{10} 210−1 = 1023−1022+1023
binary128Quadruple precision211334.02154931.77 2 14 2^{14} 214−1 = 16383−16382+16383
binary256Octuple precision223771.341978913.2 2 18 − 1 = 262143 2^{18}−1 = 262143 2181=262143−262142+262143not basic
decimal3210777.5896101−95+96not basic
decimal641016169.58384398−383+384
decimal12810343413.5861446176−6143+6144

  • 下表列出了十进制数178.125的实数表示。
  • 实数表示数值
    原式十进制数178.125
    二进制数10110010.001
    二进制浮点数表示 1.0110010001 × 2 111 1.0110010001\times{2^{111}} 1.0110010001×2111
  • 短实数表示

    • 符号移码的阶码有效位
      000000111+01111111=1000011001100100010000000000000

从真值算得其IEEE754表示形式

  • 设真值为x
    • 例 如 x = + 178.125 例如x=+178.125 x=+178.125,采用32为IEEE754规格的32位规格(8位用来保存阶码)
    • 真 值 的 二 进 制 形 式 = + 10110010.001 真值的二进制形式=+10110010.001 =+10110010.001
      • 按原码规格化该浮点数:
        • x = 0.10110010001 × 2 + 8 x=0.10110010001\times{2^{+8}} x=0.10110010001×2+8
        • x = 1.0110010001 × 2 + 7 x=1.0110010001\times{2^{+7}} x=1.0110010001×2+7
          • 可以将这种形式称为IEEE754规格化
          • 这种形式的规格化数落在[1,2)区间内
          • 即,开头总是1,这样可以不用可以用个位(bit)来存储这个1,从而可以而外的多表示移位小数(提高一点精度)
          • 其中:
            • 阶 码 E = + 7 阶码E=+7 E=+7
            • 尾 数 数 值 位 M = . 0110010001 尾数数值位M=.0110010001 M=.0110010001
              • 由于IEEE的隐藏1处理,因此尾数最终从 1.0110010001 变 为 . 0110010001 1.0110010001变为.0110010001 1.0110010001.0110010001
              • 小数点还是先出来,但是机器中不保存小数点
              • 0 ⩽ M < 1 0 \leqslant M<1 0M<1
    • 基于IEEE规格化形式的二进制串,进行阶码和位数的机器数化编码:
      • 符号位:整数用0表示,负数用1表示,本例为正数,用0编码( S f = 0 S_f=0 Sf=0)
      • 用移码来编码基数的指数(阶码), E = O ( + 7 ) = 2 7 + 7 = 1000000 0 2 + 11 1 2 = 10000111 E=O(+7)=2^7+7=10000000_2+111_2=10000111 E=O(+7)=27+7=100000002+1112=10000111
      • 用定点小数原码来编码IEEE规格化尾数数值部分, M = T ( M ) = 0110010001 M=T(M)=0110010001 M=T(M)=0110010001

从IEEE754表示形式计算其表示的真值

  • 设B=偏置值:

    • B i = { 127 , i=1,single precision,8bit阶码 1023 , i=2,double precision,11bit阶码 x = ( − 1 ) S f × 1. M × 2 E − B i ∣ x ∣ = 1. M × 2 E − B i 其 中 , 1. M = 1 + M , ( M ∈ [ 0 , 1 ) ) 注 意 这 里 的 1. M 的 1 不 是 符 号 位 ( 符 号 位 是 用 单 独 的 数 符 S f 表 示 的 ) I E E E 的 规 格 化 尾 数 的 绝 对 值 ( 换 原 被 隐 藏 的 1 ) , 也 就 是 ( 1. M ) 取 值 落 在 [ 1 , 2 ) 的 范 围 内 1. M 是 非 负 的 ( 或 者 是 无 符 号 的 ) , 它 的 符 号 位 在 头 部 ( S f ) B_i=\begin{cases} 127,&\text{i=1,single precision,8bit阶码} \\1023,&\text{i=2,double precision,11bit阶码} \end{cases} \\ \begin{aligned} \\x&=(-1)^{S_f}\times{1.M}\times{2^{E-B_i}} \\|x|&=1.M\times{2^{E-B_i}} \end{aligned} \\其中,1.M=1+M,(M\in[0,1)) \\注意这里的1.M的1不是符号位(符号位是用单独的数符S_f表示的) \\IEEE的规格化尾数的绝对值(换原被隐藏的1),也就是(1.M)取值落在[1,2)的范围内 \\1.M是非负的(或者是无符号的),它的符号位在头部(S_f) Bi={127,1023,i=1,single precision,8bit阶码i=2,double precision,11bit阶码xx=(1)Sf×1.M×2EBi=1.M×2EBi,1.M=1+M,(M[0,1))1.M1(Sf)IEEE(1),(1.M)[1,2)1.M(),(Sf)

🎈IEEE 754浮点数的表示范围

IEEE浮点数的精度和范围

一旦浮点数的位数确定后,合理分配阶码尾数位数,直接影响浮点数的表示范围和精度

  • 通常对于短实数(总位数为32位),阶码取8位(含阶符1位) ,尾数取24位(含数符1位);
  • 对于长实数(总位数为64位),阶码取11位(含阶符1位) ,尾数取53位(含数符1位);
  • 对于临时实数(总位数为80位),阶码取15位(含阶符1位) ,尾数取65位(含数符1位)。

阶码全为0/1的情况

  • 全0阶码同时全0尾数,表示 ± 0 \pm0 ±0,符号取决于数符 S f S_f Sf
    • 通常它们等效
  • 全1阶码全0尾数,表示 ± ∞ \pm\infin ±
    • 引入无穷大是为了使得计算过程中出现异常,依然能够进行下去

阶码不为全0也不为全1的情况

短浮点数
  • 1+8+23

    • 最小绝对值

      • E = 1 , M = 0 ; 对 应 的 真 值 m i n = 1. M × 2 E − B 1 = 1.0 × 2 1 − 127 = 1.0 × 2 − 126 E=1,M=0; \\对应的真值min=1.M\times{2^{E-B_1}}=1.0\times2^{1-127}=1.0\times{2^{-126}} E=1,M=0;min=1.M×2EB1=1.0×21127=1.0×2126
    • 最大绝对值:

      • E = ( 2 8 − 1 ) − 1 = 1 ⋯ 11 − 1 = 1 ⋯ 10 = 254 M = 1 − 2 − 23 对 应 的 真 值 为 : m a x = 1. M × 2 E − B 1 = ( 2 − 2 − 23 ) × 2 254 − 127 = ( 2 − 2 − 23 ) × 2 127 \\ \begin{aligned} E&=(2^8-1)-1 \\&=1\cdots{11}-1 \\&=1\cdots{10}=254 \\M&=1-2^{-23} \end{aligned} \\对应的真值为: max=1.M\times{2^{E-B_1}} =(2-2^{-23})\times2^{254-127} ={(2-2^{-23})}\times2^{127} EM=(281)1=1111=110=254=1223:max=1.M×2EB1=(2223)×2254127=(2223)×2127
长浮点数
  • 1+11+52

    • 最小绝对值

      • E = 1 , M = 0 ; 对 应 的 真 值 m i n = 1. M × 2 E − B 2 = 1.0 × 2 1 − 1023 = 1.0 × 2 − 1022 E=1,M=0; \\对应的真值min=1.M\times{2^{E-B_2}}=1.0\times2^{1-1023}=1.0\times{2^{-1022}} E=1,M=0;min=1.M×2EB2=1.0×211023=1.0×21022
    • 最大绝对值:

      • E = ( 2 11 − 1 ) − 1 = 1 ⋯ 10 = 2046 M = 1 − 2 − 52 对 应 的 真 值 为 : m a x = 1. M × 2 E − B 2 = ( 2 − 2 − 52 ) × 2 2046 − 1023 = ( 2 − 2 − 52 ) × 2 1023 \\ \begin{aligned} E&=(2^{11}-1)-1 \\&=1\cdots{10}=2046 \\M&=1-2^{-52} \end{aligned} \\对应的真值为: max=1.M\times{2^{E-B_2}} =(2-2^{-52})\times2^{2046-1023} \\={(2-2^{-52})}\times2^{1023} EM=(2111)1=110=2046=1252:max=1.M×2EB2=(2252)×220461023=(2252)×21023

机器零

  • 当一个浮点数尾数为0时(不论其阶码为何值)或阶码等于或小于它所能表示的最小数时(不管其尾数为何值)机器都把该浮点数作为零看待,并称之为“机器零”。
  • 如果浮点数的阶码用移码表示,尾数用补码表示
    • 则当阶码为它所能表示的最小数 − 2 m -2^{m} 2m(式中 m为阶码的位数,此时该浮点数已经被当作机器零)且尾数为0时,其阶码(移码)全为0,尾数(补码)也全为0,这样的机器零为000…0000

🎈移码Offset binary

  • 浮点数的表示中,采用移码的原因

    • 使用补码不容易直接判断数的大小

    • 使用移码可以直接判断出机器数对应的真值之间的大小关系

    • 移码只能够表示整数

  • [ x ] 移 在 数 轴 上 的 表 示 总 是 ⩾ 0 [x]_{移}在数轴上的表示总是\geqslant0 [x]0

  • 假设:

    • 真 值 x 的 移 码 的 二 进 制 串 为 O ( x ) = x 0 , x 1 ⋯ x n 真值x的移码的二进制串为O(x)=x_0,x_1\cdots{x_n} xO(x)=x0,x1xn

      • O ( x ) = 2 n + x , ( x ∈ [ − 2 n , 2 n − 1 ] ) O ( x ) ∈ [ 0 , 2 n + 1 − 1 ] 以 n + 1 位 二 进 制 无 符 号 数 表 示 [ 0 ⋯ 00 2 , 1 ⋯ 11 2 ] O(x)=2^n+x,(x\in[-2^{n},2^n-1]) \\O(x)\in[0,2^{n+1}-1] \\以n+1位二进制无符号数表示[0\cdots{00}_2,1\cdots{11}_2] O(x)=2n+x,(x[2n,2n1])O(x)[0,2n+11]n+1[0002,1112]

      • 如 果 数 值 位 不 足 n 位 , 则 补 0 对 齐 如果数值位不足n位,则补0对齐 n,0

      • 计算移码的偏置值通常取的就是 2 n 2^n 2n

      • 移 码 计 算 公 式 ( 移 码 函 数 O ( x ) ) 是 一 个 单 调 递 增 函 数 移码计算公式(移码函数O(x))是一个单调递增函数 (O(x))

    • 有的地方偏置值取 2 n − 1 2^n-1 2n1

移码和真值相互转换以及表示范围

  • 从移码计算真值:

    • x = O − 1 ( O ( x ) ) = O ( x ) − 2 n x=O^{-1}(O(x))=O(x)-2^n x=O1(O(x))=O(x)2n
      • x ∈ [ − 2 n , 2 n − 1 ] x\in[-2^{n},2^n-1] x[2n,2n1]
    • 此时将 O ( x ) O(x) O(x)理解为无符号数
    • O ( x ) ∈ [ 0 , 2 n + 1 − 1 ] O(x)\in[0,2^{n+1}-1] O(x)[0,2n+11]
  • 🎈相同位数n的情况下,移码可以表示的数(真值)的范围和补码一样

  • 用 函 数 O ( x ) 表 示 x 的 移 码 用函数O(x)表示x的移码 O(x)x

  • 真 值 x 1 = + 10100 ( 二 进 制 形 式 ) 真值x_1=+10100(二进制形式) x1=+10100()

    • 整 数 位 数 为 n 1 = 5 ( 没 有 显 式 给 定 机 器 字 长 , 自 行 通 统 计 x 的 二 进 制 形 式 的 位 数 ) 整数位数为n_1=5(没有显式给定机器字长,自行通统计x的二进制形式的位数) n1=5(,x)
    • (如果给定了机器字长n,需要视情况将二进制数补齐到n位)
  • O ( x 1 ) = 2 n + x = 2 5 + 1010 0 2 = 100000 + 1010 0 2 = 1 , 10100 O(x_1)=2^n+x=2^5+10100_2=100000+10100_2=1,10100 O(x1)=2n+x=25+101002=100000+101002=1,10100

    • 此处添加的逗号,将符号位和数值部分分割开来
    • 移码不用来表示小数
  • 真 值 x 2 = − 10100 ( 二 进 制 形 式 ) 真值x_2=-10100(二进制形式) x2=10100()

    • 整 数 位 数 为 n 2 = 5 整数位数为n_2=5 n2=5
  • O ( x 2 ) = 2 n + x = 2 5 − 1010 0 2 = 100000 − 1010 0 2 = 0 , 0110 O(x_2)=2^n+x=2^5-10100_2=100000-10100_2=0,0110 O(x2)=2n+x=25101002=100000101002=0,0110

  • 真 值 x = ± 0 ( 二 进 制 形 式 ) 真值x=\pm0(二进制形式) x=±0()

    • 整 数 位 数 为 n 整数位数为n n
  • O ( ± 0 ) = 2 n ± 0 = 2 n = 2 n = 1 , 0 ⋯ 00 O(\pm0)=2^{n}\pm0=2^{n}=2^n=1,0\cdots{00} O(±0)=2n±0=2n=2n=1,000

  • 可 见 , ± 0 可见,\pm{0} ,±0移码的表示形式是相同的,真值0的补码具有唯一性

  • 此外,由移码的定义可见,当n = 5时,其最小的真值为 x = − 2 5 = − 10000 0 二 进 制 x = -2^{5}=- 100000_{二进制} x=25=100000,则 [ − 100000 ] 移 = 2 5 + x = 100000 − 100000 = 0 , 00000 [ - 100000]_{移} =2^{5}+ x = 100000 - 100000 = 0,00000 [100000]=25+x=100000100000=0,00000,即最小真值的移码为全0,这符合人们的习惯。
  • 利用移码的这一特点,当浮点数的阶码用移码表示时,就能很方便地判断阶码的大小

C语言和浮点数类型

  • C语言中的浮点数类型及类型转换.
  • C语言中的float和double类型分别对应于IEEE 754单精度浮点数(32bit)双精度浮点数(64bit)
    • long double类型对应于扩展双精度浮点数,但long double的长度和格式随编译器和处理器类型的不同而有所不
      同。
  • 在C程序中等式的赋值和判断中会出现强制类型转换
    • 以char> int>long> double和float>double最为常见,
    • 从前到后范围和精度都从小到大,转换过程没有损失。
  • 从int转换为float时(通常,它们都是32bit),虽然不会发生溢出
    • 但int可以保留32位,float保留24位(包括隐藏位),可能有数据舍入(可能影响精度)
      • 具体是:当int类型的 25 ∼ 31 25\sim{31} 2531bit这些位非0,就无法被无损的转换为浮点数
      • 因此,如果可以用整形表示的数尽量用整形,不经可以保证精度也可以保证运算效率
    • 若从int转换为double则不会出现精度受损
      • 应为double类型的精度达到53位明显大于31位(不计符号位)
        • double的有效位数更多,因此能保留精确值。
      • 因此不能够笼统的认为,整数转为浮点数,精度一定下降(要区分单精度和双精度)
      • 就算是单精度,也要考虑被转换的数的结构!
    • long到double同样可能会损失精度(但是不总是损失,以被转换的数据小数情况共同考虑)
  • 从double 转换为float 时,因为float 表示范围更小,因此可能发生溢出
    • 此外,由于有效位数变少,因此可能被舍入。
  • 从float或double转换为int时,因为int没有小数部分
    • 所以数据可能会向0方向被截断(仅保留整数部分),影响精度。
      • 浮点数x向0方向阶段,就是绝对值被向下取整
      • 123.45 → 123 123.45\to{123} 123.45123
      • − 123.45 → − 123 -123.45\to{-123} 123.45123
    • 另外,由于int的表示范围更小,因此可能发生溢出。
      • 31位数值位的上限 2 31 − 1 2^{31}-1 2311
      • 单精度的float具有8位阶码(7位数值位,上限为 2 2 7 − 1 = 2 127 2^{2^{7}-1}=2^{127} 2271=2127
      • 双精度的范围就更大了,达到 2 1023 2^{1023} 21023
      • 可见差距十分悬殊
posted @   xuchaoxin1375  阅读(29)  评论(0编辑  收藏  举报  
相关博文:
阅读排行:
· 全程不用写代码,我用AI程序员写了一个飞机大战
· MongoDB 8.0这个新功能碉堡了,比商业数据库还牛
· 记一次.NET内存居高不下排查解决与启示
· 白话解读 Dapr 1.15:你的「微服务管家」又秀新绝活了
· DeepSeek 开源周回顾「GitHub 热点速览」
点击右上角即可分享
微信分享提示