问题描述
我正在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位结果是预期的(值相同,退出代码非零)在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?
编辑:这不同于因为这里所有的值都是双倍的。
this is different from Why comparing double and float leads to unexpected result? because here all the values are double.
推荐答案
IEEE-754允许以更高的精度(强调我的)完成中间计算。
IEEE-754 allows intermediate computations to be done in a greater precision (emphasis mine).
在您的情况下,例如在IA-32上,双精度值可以更精确地存储在x87 FPU寄存器中(80位而不是64位) 。所以你实际上是将双重精度乘法与双倍扩展精度乘法相比较。
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,因为使用SSE),添加 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:
这篇关于32位平台的编译时间和运行时间之间的双乘法不同的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!