我有一些简单的代码比较两个浮点值来说明我看到的GCC优化的问题,并希望有人能帮助我弄清楚为什么它产生的输出在一些下有所不同可重复的情况。GCC处理在不同的优化级别上浮点数比较不同
首先,我知道将浮点值与==比较是不好的,因为尾数可能会有一些非常小的数值,但在我的示例中情况并非如此。我遇到的问题是基于2个因素的输出更改。 1)我传入的优化标志,以及2)如果我取消注释std :: cout行。
为什么GCC代码在-O2下产生不同的运行? 如果我取消注释打印,为什么在-O2下编译的代码工作?
这里是我正在测试的代码:
#include <iostream>
const float ft_to_m = (float)0.3048;
const float m_to_ft = (float)3.28083989501;
float FeetToKilometers(float & Feet) {
float Kilometers;
Kilometers = (ft_to_m * Feet)/1000.;
return Kilometers;
}
int main(void)
{
float feet = 20000.;
float old_val = 0;
float new_val = FeetToKilometers(feet);
float diff_val = 0;
int *old_int = reinterpret_cast<int*>(&old_val);
int *new_int = reinterpret_cast<int*>(&new_val);
for (int i=0; i<2; i++)
{
new_val = FeetToKilometers(feet);
diff_val = old_val-new_val;
//std::cout << "Random COUT that makes this work" << std::endl;
if(old_val==new_val)
{
std::cout << "old_val==new_val" << std::endl;
std::cout << std::hex << *old_int << "," << std::hex << *new_int << std::endl;
std::cout << "diff_val = " << diff_val <<std::endl;
}
else
{
std::cout << "old_val!=new_val" <<std::endl;
std::cout << std::hex << *old_int << "," << std::hex << *new_int << std::endl;
std::cout << "diff_val = " << diff_val <<std::endl;
old_val=FeetToKilometers(feet);
}
}
return 0;
}
当与-O0,-O1,和-O3(克++ -O TEST.CPP)在Linux/cygwin的编译时,得到以下输出:
$ ./a.exe
old_val!= new_val
0,40c3126f
diff_val = -6.096
old_val == new_val
40c3126f,40c3126f
diff_val = 0
即输出是正确的,可以看到的浮标(new_val和old_val)的比特是相同的。当我与-02标志(G ++ -02 TEST.CPP)编译我得到以下:
$ ./a.exe
old_val = new_val
0,40c3126f
diff_val = -6.096
old_val!= new_val
40c3126f,40c3126f
diff_val = 1.19209e-07
我会考虑这个输出错误。即使这两个值是相同位智者,扣除他们和==检查表明他们是不同的。
$ ./a.exe
随机COUT:如果我再取消对性病::法院线,并与-02标志(G ++ -02 TEST.CPP)我得到以下重建这使得这项工作
old_val!= new_val
0,40c3126f
diff_val = -6。096
随机COUT,使得这项工作
old_val == new_val
40c3126f,40c3126f
diff_val = 1.19209e-07
这在old_val == new_val正确的,即使减法仍然略有差异。
此代码也可以-02下,如果脚是2000年,而不是20000
任何人都可以解释为什么编译后的代码的行为就像这样?我想知道为什么2位相同的浮点值不能与==比较。
gcc版本3.4.4
+1。这是(几乎肯定)的问题。无论优化级别如何,使用“-ffloat-store”选项进行编译都会得到一致的结果。 – eldarerathis 2010-09-21 23:41:31
好吧,也许我是一个noob,但你应该怎么做浮点比较? <= and > =?只需链接到相关信息就足够了。谢谢。 – 2010-09-22 00:16:55
@Robert:'fabs(a-b)
2010-09-22 00:42:03