Chinaunix首页 | 论坛 | 博客
  • 博客访问: 317753
  • 博文数量: 57
  • 博客积分: 146
  • 博客等级: 入伍新兵
  • 技术积分: 769
  • 用 户 组: 普通用户
  • 注册时间: 2012-05-29 14:57
文章分类
文章存档

2014年(39)

2013年(13)

2012年(5)

我的朋友

分类: C/C++

2014-07-03 16:00:54

浮点指的是带有小数的数值,浮点运算即是小数的四则运算,常用来测量电脑运算速度。大部份计算机采用二进制(b=2)的表示方法。位(bit)是衡量浮点数所需存储空间的单位,通常为32位或64位,分别被叫作单精度和双精度。有一些计算机提供更大的浮点数,例如英特尔公司的浮点运算单元Intel8087协处理器(以及其被集成进x86处理器中的后代产品)提供80位长的浮点数,用于存储浮点运算的中间结果。还有一些系统提供128位的浮点数(通常用软件实现)。
在计算机使用的浮点数被电气电子工程师协会(IEEE)规范化为IEEE 754。


单精度在32位机上的二进制表示:

The bit pattern b1b2b3...b9b10b11...b32  of a word in a 32-bit machine represents the real number:
       (-1)s x 2e-127 x (1.f)2         where s = b1,  e = (b2...b9)2, and f = b10b11...b32.  

符号位  偏差指数位  规约形式尾数的小数位
1 bit 8 bits 23 bits
s e f


IEEE 标准要求浮点数尾数的小数点二进制表示左侧必须为 1,因此我们在保存尾数的时候,可以省略小数点前面这个 1,从而腾出一个二进制位来保存更多的尾数。这样我们实际上用 23 位长的尾数域表达了 24 位的尾数。比如二进制的 1001.101(对应于十进制的 9.625)可以表达为 1.001101 × 2^(3),所以实际保存在尾数域中的值为 00110100000000000000000,即去掉小数点左侧的 1,并用 0 在右侧补齐。



双精度在32位机上二进制表示:
The bit pattern b1b2b3...b12b13b14...b64  of two words in a 32-bit machine represents the real number
       (-1)s x 2e-1023 x (1.f)2      where s = b1,  e = (b2...b12)2, and f = b13b14...b64.

符号位 偏差指数位  规约形式尾数的小数位 
1 bit 11 bits 52 bits
s e f

IEEE 标准要求浮点数尾数的小数点二进制表示左侧必须为 1,因此我们在保存尾数的时候,可以省略小数点前面这个 1,从而腾出一个二进制位来保存更多的尾数。这样我们实际上用 52 位长的尾数域表达了 53位的尾数。

为了处理负指数的情况,实际的指数值按要求需要加上一个偏差(Bias)值作为保存在指数域中的值,单精度数的偏差值为 127,而双精度数的偏差值为 1023。比如,单精度的实际指数值 0 在偏差指数域中将保存为 127;而保存在指数域中的 64 则表示实际的指数值 -63。 偏差的引入使得对于单精度数,实际可以表达的指数值的范围就变成 -127 到 128 之间(包含两端)。

如二进制的 1001.101(对应于十进制的 9.625)可以表达为 1.001101 × 2^(3),所以实际保存在尾数域中的值为 00110100000000000000000,即去掉小数点左侧的 1,并用 0 在右侧补齐。偏差指数域则是10000010等于130(130-127),因为是正数符号位0.所以9.625的二进制表示0 10000010 00110100000000000000000。


1.规约形式的浮点数
如果浮点数中偏差指数部分的编码值在0 < exponent < 2^(e-1)之间,且尾数部分最高有效位(即整数字)是1,那么这个浮点数将被称为规约形式的浮点数.
2.非规约形式的浮点数
如果浮点数的指数部分的编码值是0,尾数为非零,那么这个浮点数将被称为非规约形式的浮点数。IEEE 754标准规定:非规约形式的浮点数的指数偏移值比规约形式的浮点数的指数偏移值大1.例如,最小的规约形式的单精度浮点数的指数部分编码值为1,指数的实际值为-126;而非规约的单精度浮点数的指数域编码值为0,对应的指数实际值也是-126而不是-127。实际上非规约形式的浮点数仍然是有效可以使用的,只是它们的绝对值已经小于所有的规约浮点数的绝对值;即所有的非规约浮点数比规约浮点数更接近0。规约浮点数的尾数大于等于1且小于2,而非规约浮点数的尾数小于1且大于0.

特殊值
这里有三个特殊值需要指出:

1.如果指数是0并且尾数的小数部分是0,这个数±0(和符号位相关)
2.如果指数 = 2^(e-1)并且尾数的小数部分是0,这个数是±∞(同样和符号位相关)
3.如果指数 = 2^(e-1)并且尾数的小数部分非0,这个数表示为不是一个数(NaN)。

以上规则,总结如下:


浮点数的比较
浮点数基本上可以按照符号位、指数域、尾数域的顺序作字典比较。显然,所有正数大于负数;正负号相同时,指数的二进制表示法更大的其浮点数值更大。

浮点数的运算与函数
标准运算
下述函数必须提供:
1.加减乘除Add, subtract, multiply, divide.在加减运算中负零与零相等 -0.0 = 0.0
2.平方根Square root. sqrt(x) ≥ 0 (x≥0),另规定sqrt(-0.0) = -0.0
3.浮点余数。返回值x - (round(x / y) * y).
4.近似到最近的整数round(x).如果恰好在两个相邻整数之间,则近似到偶数。
5.比较运算. -Inf <负的规约浮点数数<负的非规约浮点数< -0.0 = 0.0 <正的非规约浮点数<正的规约浮点数< Inf;
特殊比较: -Inf = -Inf, Inf = Inf, NaN与任何浮点数(包括自身)的比较结果都为假,即 (NaN ≠ x) = false.(inf正无穷大,-inf负无穷小)

点击(此处)折叠或打开

  1. #include <stdio.h>
  2. #include <limits.h>
  3. #include

  4. int main(void)
  5. {
  6.     float x = 9.625;
  7.     float a = x/0.0;
  8.     float b = x/-0.0;
  9.     float c = sqrtf(-1.0);
  10.     
  11.     printf("%f, %f, %f\n", c, a, b);

  12.     return 0;
  13. }
输出:

点击(此处)折叠或打开

  1. -nan, inf, -inf,



阅读(624) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~