【发布时间】:2011-03-15 21:07:51
【问题描述】:
考虑一个双精度类型的类
class path_cost {
double length;
double time;
};
如果我想按字典顺序排列path_costs 的列表,我遇到了问题。继续阅读:)
如果我像这样在相等性测试中使用完全相等
bool operator<(const path_cost& rhs) const {
if (length == rhs.length) return time < rhs.time;
return length < rhs.length;
}
生成的顺序很可能是错误的,因为一个小的偏差(例如由于长度计算中的数值不准确)可能会导致长度测试失败,因此例如
{ 231.00000000000001, 40 } < { 231.00000000000002, 10 }
错误地持有。
如果我也可以使用这样的容差
bool operator<(const path_cost& rhs) const {
if (std::fabs(length-rhs.length)<1-e6)) return time < rhs.time;
return length < rhs.length;
}
那么排序算法可能会严重失败,因为
有什么想法吗?解决方案?我考虑过对实线进行分区,以便每个分区内的数字被认为是相等的,但这仍然留下太多相等测试失败但不应该失败的情况。
(James Curran 更新,希望能解释问题): 给定数字:
- A = {231.0000001200, 10}
- B = {231.0000000500, 40}
-
C = {231.0000000100, 60}
- A.Length 和 B.Length 相差 7-e7,因此我们使用时间,而 A
- B.Length & C.Length 相差 4-e7,所以我们使用时间,B
- A.Length 和 C.Length 相差 1.1-e6,因此我们使用长度,并且 A > C。
(由 Esben Mose Hansen 更新) 这不是纯粹的理论。当给定非传递排序运算符时,标准排序算法往往会崩溃或更糟。这正是我一直在努力解决的问题(男孩调试起来很有趣;))
【问题讨论】: