c++ - 浮点比较的不可再现性

标签 c++ floating-accuracy

我和我的博士。学生在物理数据分析环境中遇到了一个问题,我可以对此有所了解。我们有代码分析来自 LHC 实验之一的数据,该实验给出了不可重复的结果。特别是,在同一台机器 上运行的相同二进制文件 的计算结果可能会因连续执行而异。我们知道不可再现性的许多不同来源,但排除了常见的嫌疑人。

当比较两个名义上具有相同值的数字时,我们将问题归结为( double )浮点比较操作的不可再现性。由于分析中的先前步骤,偶尔会发生这种情况。一个例子我们刚刚找到了一个测试数字是否小于 0.3 的例子(注意我们从不测试浮点值之间的相等性)。事实证明,由于检测器的几何形状,计算有时可能会产生恰好为 0.3(或其最接近的 double 表示)的结果。

我们很清楚比较 float 时的陷阱,也很清楚 FPU 中过高的精度可能会影响比较结果。我想回答的问题是“为什么结果无法重现?”是不是因为 FPU 寄存器加载或其他 FPU 指令没有清除多余的位,因此以前计算的“剩余”位影响了结果? (这似乎不太可能)我在另一个论坛上看到一个建议,进程或线程之间的上下文切换也可能导致浮点比较结果发生变化,因为 FPU 的内容存储在堆栈中,因此被截断。对这些=或其他可能的解释的任何评论将不胜感激。

最佳答案

猜测是,您的计算通常是在 FPU 内执行的,精度更高,并且仅在特定点进行舍入(例如,当您将结果分配给一个值时)。

但是,当存在上下文切换时,必须保存和恢复 FPU 的状态——并且至少很有可能这些额外的位不会被保存和恢复上下文切换。当它发生时,这可能不会引起重大变化,但如果(例如)您稍后从每项中减去固定金额并乘以剩余的金额,差额也会成倍增加。

明确一点:我怀疑“遗留”位是罪魁祸首。相反,它会丢失额外的位,导致在计算中略有不同的点进行舍入。

关于c++ - 浮点比较的不可再现性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5008628/

相关文章:

math - float 学坏了吗?

c++ - 有没有办法从 pcrecpp 获取 PREMATCH ( $`) and POSTMATCH ($' )?

c++ - 使用 libc++ 和 libstdc++ 的 void* 类型的字符串流行为差异

用于搜索和索引的 C++ 框架,如 clucene

c++ - 如何检查 float 的依赖关系

math - float 学有问题吗?

javascript - 为什么具有精确值的 float 之和仍然取决于顺序?

math - float 学有问题吗?

c++ - 将 RANSAC 应用于 vector<Point2f> 以进行相似性变换

c++ - Qt:当 boundingRect() 中心不在 View 中时,自定义 QGraphicsItem 不显示