Visual c++ x64 VS2019-VS2015中的非一致性比较
我有一个简单的程序:Visual c++ x64 VS2019-VS2015中的非一致性比较,visual-c++,visual-studio-2019,Visual C++,Visual Studio 2019,我有一个简单的程序: #include <iostream> #include <cmath> int main() { double dNan = std::nan("nan"); double dNotNan = 3961.12345; if (dNan == dNotNan) std::cout << "Nan == Not Nan" << std::endl; else st
#include <iostream>
#include <cmath>
int main()
{
double dNan = std::nan("nan");
double dNotNan = 3961.12345;
if (dNan == dNotNan)
std::cout << "Nan == Not Nan" << std::endl;
else
std::cout << "Nan != Not Nan" << std::endl;
}
对于平台x86或/fp:precise,输出为预期的“Nan!=非Nan”
为比较生成的汇编程序为:
00007FF6F8E7101F ucomisd xmm0,mmword ptr [__real@40aef23f34d6a162 (07FF6F8E732B8h)]
00007FF6F8E71027 je main+30h (07FF6F8E71030h)
在哪里__real@40aef23f34d6a162是3961.12345值,xmm0包含NaN“0000000000000000-7FF800000000000”。UCOMISD指令的结果是标志ZP、CF、PF全部设置,这表示“无序”,即至少有一个操作数为NaN。JE指令仅测试ZF标志,当两个操作数相等时,ZF标志设置为1
文件中说“特殊值(NaN,+无穷大,-无穷大,-0.0)可能不会传播或严格遵守IEEE-754标准”,其他地方给出的例子为NaN-NaN=0,但比较行为似乎远远超出了“不严格遵守标准”
我找不到这方面的任何信息;这真的是预期的行为还是我刚刚被编译器错误绊倒了?
/fp:strict
在计算上比/fp:precise
更昂贵,因为编译器必须插入额外的指令来捕获异常,并允许程序在运行时访问或修改浮点环境。如果您的代码不使用此功能,但需要源代码排序和舍入,或依赖于特殊值,请使用/fp:precise
。有关更多详细信息,我建议您可以参考链接:“/fp:fast
适用于不依赖于处理特殊值(如NaN)的标准规则的程序。”你似乎很在意——所以不要使用/fp:fast
@Igor谢谢;是的,看起来这就是必须发生的事情。问题是,从快速到精确的转换不仅会降低计算速度(这可能是正常的),而且还会以不可预测的方式改变计算结果(这可能不是)。@Jeaninez是的,这里出现的问题是x86和x64编译器之间的行为差异。这意味着客户可以同时运行当前的32位软件和新的64位版本,并查看输出中的差异。
00007FF6F8E7101F ucomisd xmm0,mmword ptr [__real@40aef23f34d6a162 (07FF6F8E732B8h)]
00007FF6F8E71027 je main+30h (07FF6F8E71030h)