【发布时间】:2021-01-29 11:54:12
【问题描述】:
我需要为具有唯一哈希码的未知对象类型生成一系列“默认值”。 (可以是结构或类,重写 GetHashCode 使其默认构造始终返回相同的哈希值。)
为了处理大多数此类情况,我使用反射来查找可以排序的数字字段/属性。因此,例如,如果我能找到一个双字段,我可以继续为该字段返回具有不同值的新对象,这通常会改变哈希值。
那么如何形成这个值序列呢?起初我以为我只需要坚持整数分辨率的范围,并且每次迭代都可以继续添加 1.0。基于this answer,我选择了-1E50到1E50的范围。但事实证明 Double.GetHashCode 为 -1E50 和 (-1E50 + 1.0) 返回相同的哈希值。将范围降低到 -1E15 到 1E15 似乎可以解决它,但我仍然不知道我正在做的事情是否安全。 (我不需要这么大的范围,但我确实需要知道我不会发生碰撞。)
所以我的问题是,我可以使用什么范围的双精度值(每次递增 1.0 或其他数量)来保证不同的哈希结果?对于浮点数或其他数字类型,此答案是否会改变?
【问题讨论】:
-
如果一个类有 int a;字符串 s;数据成员 - 我们不要(在 GetHashCode 覆盖中)类似 - return a.GetHashCode() ^ s.GetHashCode(); ——这有什么问题?
-
@Prateek OP 缺少
-1E50和-1E50 + 1成为相同值的点。 -
不,它不安全,双打不能保持那种精度。
-
请注意,您应该将
GetHashCode返回的值用于潜在相等。因为你在归类更大的价值,所以总会有碰撞的空间。您需要检查实际值以确认相等。