在32位平台上编译时和运行时之间双倍增不同 [英] Double multiplication differs between compile time and runtime in 32 bit platform
问题描述
我编译和32位和64位平台上运行下面的程序:
I'm compiling and running the following program in 32 and 64 bit platforms:
int main()
{
double y = 8.34214e08;
double z = 1.25823e45;
return y * z == 8.34214e08 * 1.25823e45;
}
而在64位的结果被预期(的值是相同的,并出射code是非零)在32位似乎还有在编译时计算出的值之间的差别不大,右手侧的比较,和左侧在运行时计算
While in 64bit the result is the expected (the values are the same and the exit code is non-zero) in 32bit seems there is a little difference between the value calculated at compile time, the right hand side of the comparison, and the left side computed at runtime.
这是在编译器错误或有一个合理的解释?
Is this a bug in the compiler or there is a logical explanation?
编辑:这是从不同,为什么比较double和float导致意想不到的结果,因为这里所有的值都是双
this is different from Why comparing double and float leads to unexpected result? because here all the values are double.
推荐答案
IEEE-754允许中间计算在更大precision(重点矿山)完成。
IEEE-754 allows intermediate computations to be done in a greater precision (emphasis mine).
(IEEE-754:2008)一个语言标准也应定义,并且需要实现来提供,属性,允许和禁止的值变化的优化,单独地或共同地,对于一个块这些优化可能包括,但并非如此。限于:[...] 的前pression评价更广泛的中间结果使用
(IEEE-754:2008) "A language standard should also define, and require implementations to provide, attributes that allow and disallow value-changing optimizations, separately or collectively, for a block. These optimizations might include, but are not limited to: [...] Use of wider intermediate results in expression evaluation."
在您的情况下,例如在IA-32,双值可以存储在具有更大precision(80位而不是64)的的x87 FPU寄存器。所以,你实际上是比较双precision完成对双扩展precision做了乘法的乘积。
In your case for example on a IA-32, the double values could be stored in the x87 FPU registers with greater precision (80-bit instead of 64). So you are actually comparing a multiplication done on double precision with a multiplication done on double-extended precision.
例如,在x64那里的结果是 1
(不使用的x87 FPU上交所来代替),加入 GCC
选项 -mfpmath = 387
来使用的x87使我的机器上的结果改变 0
。
For example, on x64 where the result is 1
(the x87 FPU is not used as SSE is used instead), adding gcc
option -mfpmath=387
to use the x87 makes the result change to 0
on my machine.
如果你不知道这是否也是用C允许的,它是:
And if you wonder if that is also allowed by C, it is:
(C99,6.3.1.p8)浮操作数和浮动前pressions的结果的值可被重新psented更大precision和范围比由类型所要求$ P $ ;
(C99, 6.3.1.p8) "The values of floating operands and of the results of floating expressions may be represented in greater precision and range than that required by the type;"
这篇关于在32位平台上编译时和运行时之间双倍增不同的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!