如何用C表示内存中的FLOAT编号

时间:2011-08-02 09:46:03

标签: c floating-point

在阅读教程时,我遇到了如何在内存中表示浮点数。本教程有一个带浮点数的例子。

   float a=5.2  with below Diagram

enter image description here

任何人都可以告诉我们5.2如何转换成二进制文件以及如何在上图中的内存中表示它?

11 个答案:

答案 0 :(得分:50)

如前所述,5.2表示为符号位,指数和尾数。你怎么编码5.2?

5很容易:

101. 

其余的,0.2是1/5,所以将1.00000...(十六进制)除以5得到0.3333333...(十六进制)。

(如果考虑少一点,可以更容易地遵循这一点:0.FFFF...F / 5 = 3,因此很容易看到0.FFFF... / 5 = 0.33333...。在除以5时很重要,所以1.0000... / 5 = 0.3333...也是如此。

那应该给你

0.0011001100110011001100110011... 

添加5,你得到

101.00110011001100110011...         exp 0    (== 5.2 * 2^0)

现在向右移动(将其标准化,即确保最高位在小数点之前)并相应地调整指数:

1.010011001100110011001100110011... exp +2   (== 1.3 * 2^2 == 5.2)

现在你只需要向指数添加127的偏差(即129 = 0b10000001)并存储它:

0 10000001 1010 0110 0110 0110 0110 0110 

忘记尾数的前1个(除了一些特殊值,它总是应该是1,因此它不存储),你得到:

01000000 10100110 01100110 01100110

现在你只需要决定小端或大端。

这不完全是如何工作的,但是当5.2之类的数字转换为二进制时,或多或少会发生这种情况。

答案 1 :(得分:48)

我认为图表不是一个正确的百分之百。

浮点数存储在内存中,如下所示:

它们被分解为:

  • 签署s(表示是正面还是负面) - 1位
  • 尾数m(基本上是您的号码的数字--24位
  • exponent e - 7位

然后,您可以将x写为s * m * 2^e,其中^表示取幂。

5.2应表示如下:

0 10000001 01001100110011001100110    
S    E               M

S=0表示它是一个正数,即s=+1

E将被解释为无符号数,因此代表129。请注意,您必须从E中减去127才能获得原始指数e = E - 127 = 2

M必须按以下方式解释:它被解释为以1开头,后跟一个点(.),然后是该点之后的数字。 .之后的数字是m中实际编码的数字。我们为每个数字引入权重:

bits in M: 0   1    0     0      1       ... 
weight:    0.5 0.25 0.125 0.0625 0.03125 ... (take the half of the previous in each step)

现在总结设置相应位的权重。完成此操作后,您添加1(由于IEEE标准中的规范化,您总是添加1来解释M)并获取原始m

现在,您计算x = s * m * 2^e并获取原始数字。

因此,唯一剩下的就是在实内存中,字节可能是相反的顺序。这就是为什么数字可能不会存储如下:

0 10000001 01001100110011001100110    
S    E               M

但更多的是相反(只需要采用8位块并镜像它们的顺序)

01100110 01100110 10100110 01000000
MMMMMMMM MMMMMMMM EMMMMMMM SEEEEEEE

答案 2 :(得分:6)

该值以相反的顺序表示在存储器中,但由于浮点值的精度损失,混淆点可能是5.2f实际上表示为5.1999998。

答案 3 :(得分:4)

在二进制逻辑中表示5.2非常简单:

     8 4 2 1
5 -> 0 1 0 1

对于十进制数字:

取.2并乘以2(因为它以二进制表示)。

.2 X 2 = 0.4 -> take the value after the
                decimal point, don't take the value before
                the decimal point

.4 X 2 = 0.8
.8 X 2 = 1.6
.6 X 2 = 1.2
.2 X 2 = 0.4

依旧......

在此步骤之后,从上述步骤的输出中取小数点前的值:

.2 X 2 = 0.4 -> take 0 from this for representing in binary form

所以5.2的最终o / p是:

0101.00110...

答案 4 :(得分:3)

Raw float 5.2:

01000000101001100110011001100110
^ sign bit

在内存中,反向字节顺序(如图所示):

01100110011001101010011001000000
                        ^ sign bit

答案 5 :(得分:1)

5.2

数字以“符号位,指数,尾数”的形式存储。 以二进制形式5为8 4 2 1所以0101 和.2是

.2*2=.4   0
.4*2=.8   0
.8*2=1.6  1

并且对位0进行符号因为Number为正。

0 0101 001....

答案 6 :(得分:1)

5.2二进制101.00110011 ...... ------>非标准化形式 5.2是.10100110011 .... x 2 ^ 3 ------>明确的正常形式 5.2是隐式正常形式的.0100110011 x 2 ^ 3

  

这里符号位变为0(因为数字为正)和指数   是七位所以它使用超过64指数表示法所以指数   将变为64 + 3 = 69即1000101并且剩余将是尾数   (总共32位--7指数位 - 1位符号= 24位)0100 1100 1100   1100 1100 1100

在上面的示例中,符号位是正确的 超出64未应用,因此未标准化,但理想情况下应使用隐式标准化 如果应用隐式归一化,则尾数部分在第二个字节中,MSB“1”将不会到来。

答案 7 :(得分:0)

5.2表示为“01000000101001100110011001100110”

检查Converter Applet

答案 8 :(得分:0)

最初在其他网站上发布的转换技术显示出不必要的复杂(尽管它需要我们正确回答)。对于内存中5.2的内存表示:

首先将其转换为简单的二元系统,这将给我们101.001100110011001100110011

现在将其更改为科学形式:1.01001100110011001100110011 x 10 ^ 2。

现在我们的符号位为0,因为数字为正

对于指数,我们需要(127 + 2)高达8位,这给我们10000001

分数为01001100110011001100110。 (23位)(丢弃科学形式的前导1)

=>表示是

  

0 10000001 0100 1100 1100 1100 1100 110

答案 9 :(得分:0)

以下两篇参考资料确实帮助我理解了二进制格式的IEEE 754浮点数编码,

http://www.pitt.edu/~juy9/142/slides/L3-FP_Representation.pdf

http://en.wikipedia.org/wiki/Single-precision_floating-point_format

答案 10 :(得分:0)

int a;
float b=5.2;
memcpy(&a, &b, 4);
printf("%d",a);

这给出0100 0000 1010 0110 0110 0110 1000 0001 (1084647041)