【问题标题】:Fast hash function with collision possibility near SHA-1在 SHA-1 附近具有碰撞可能性的快速哈希函数
【发布时间】:2015-04-23 23:44:17
【问题描述】:

我正在使用 SHA-1 来检测程序处理文件中的重复项。它不需要是加密强的,并且可能是可逆的。我找到了这个快速哈希函数列表https://code.google.com/p/xxhash/

如果我想要在 SHA-1 附近的随机数据上获得更快的函数和冲突,我应该选择什么?

也许 128 位散列足以用于文件重复数据删除? (与 160 位 sha-1 相比)

在我的程序中,哈希是根据 0 - 512 KB 的块计算的。

【问题讨论】:

  • 使用 git 使用的那个。如果对 git 足够好,对你也足够好!
  • Git 使用 SHA-1,Git 工作流程的“热循环”显然不是 Git 提交。 OP 和我对可用于 ~hot 循环的哈希函数(例如考虑内存数据库)感兴趣,并提供非常强大的冲突保证和位独立性等。
  • CPU“快速”可能无关紧要——I/O 可能几乎是所有经过的时间。
  • granted.but 考虑重新散列一个 in-mem k/v。但你说得有道理。
  • @Stig 你看过 Blake2B 吗? blake2.net C 版本与 MD5 一样快,并且是加密的。我写了一个 Java 版本,但我无法让它比 SHA-1 更快。 github.com/alphazero/blake2b

标签: performance hash sha murmurhash


【解决方案1】:

也许这会对您有所帮助: https://softwareengineering.stackexchange.com/questions/49550/which-hashing-algorithm-is-best-for-uniqueness-and-speed

碰撞罕见:FNV-1、FNV-1a、DJB2、DJB2a、SDBM 和 MurmurHash

我不知道 xxHash,但它看起来也很有希望。

MurmurHash 非常快,版本 3 支持 128 位长度,我会选择这个。 (在 Java 和 Scala 中实现。)

【讨论】:

  • 谢谢。接受的答案本质上是经验性的,样本集是 2^20,很小:)
  • 没有一般的最佳哈希函数。它始终取决于您想要实现什么以及您的真实实时数据是什么。为你的用例做你自己的测试;)
【解决方案2】:

由于在您的情况下哈希算法的唯一相关属性是碰撞概率,您应该估计它并选择满足您要求的最快算法。

如果我们假设您的算法具有绝对一致性,则使用具有 d 个可能值的哈希的 n 个文件之间发生哈希冲突的概率将为:

例如,如果您需要在一百万个文件中的冲突概率低于百万分之一,则需要有超过 5*10^17 个不同的哈希值,这意味着您的哈希值至少需要 59位。让我们四舍五入到 64 以说明可能的不均匀性。

所以我会说任何体面的 64 位哈希对你来说应该足够了。更长的哈希将进一步降低冲突概率,代价是计算量更大,哈希存储量增加。 CRC32 等较短的缓存需要您编写一些显式的冲突处理代码。

【讨论】:

  • 没有意识到赏金会默认。如果由我决定给你的话。
  • 这太讨人喜欢了,谢谢!请记住,自动奖励的赏金会损失一半的价值,因此最好手动奖励它们,即使您选择了投票最多的答案。
  • 假设这些算法具有绝对一致性就像说地球是一个完美的球体。这在某些情况下可能很好,但如果您关心细节,这将毫无用处。它只是用于估计您所需的哈希长度。
  • 除此之外,在进行大量散列时,您很可能会受到 IO 限制
  • @A.Binzxxxxxx 好吧,这正是我在这里所做的:在给定目标碰撞概率的情况下估计哈希长度的下限。
【解决方案3】:

Google 开发并使用(我认为)FarmHash 进行性能关键的哈希。来自project page

FarmHash 是 CityHash 的继承者,包含许多相同的技巧和技术,其中一些取自 Austin Appleby 的 MurmurHash。

...

在具有所有必要机器指令的 CPU 上,大约六种不同的哈希函数可以为 FarmHash 的阵容做出贡献。在某些情况下,通过使用现在普遍可用的更新指令,我们在 CityHash 上取得了显着的性能提升。不过,我们也通过其他方式提高了一些速度,因此绝大多数使用 CityHash 的程序在切换到 FarmHash 时应该至少会有所提升。

(CityHash 已经是 Google 的性能优化哈希函数系列。)

它是在一年前发布的,当时几乎可以肯定它是最先进的,至少在已发布的算法中是这样。 (否则 Google 会使用更好的东西。)很有可能它仍然是最佳选择。

【讨论】:

  • 实际上只是在查看他们撕毁 CityHash 的 HN 讨论。 news.ycombinator.com/item?id=4600425 :(
  • 你知道它是否也适用于 FarmHash 吗?无论哪种方式,我们都在谈论非加密哈希,所以所有的赌注都是针对恶意输入的。
  • (可能重复)不,我没有。我听到了,但这可能只是语义上的区别。为什么这么容易找出碰撞?另外,让我们记住:错误.. :)
  • 仅供参考,我将使用 SipHash。没有关于 FarmHash 的消息,但请查看已发布的对各种功能的攻击,包括 Murmur3:131002.net/siphash(论文值得一读。)
【解决方案4】:

事实:

  1. 良好的散列函数,特别是加密函数(如 SHA-1), 需要相当多的 CPU 时间,因为它们必须遵守许多 在这种情况下对你来说不是很有用的属性;
  2. 任何散列函数只会给你一个确定性:如果两个文件的散列值不同,则文件肯定不同。但是,如果它们的哈希值相等,则文件也可能相等,但是确定这种“相等”是否不仅仅是哈希冲突的唯一方法是回退到两者的二进制比较文件。

结论:
在你的情况下,我会尝试一个更快的算法,比如 CRC32,它几乎具有你需要的所有属性,并且能够处理超过 99.9% 的情况,并且只采用较慢的比较方法(如二进制比较)来排除误报。在绝大多数比较中更快可能会弥补没有“令人敬畏”的均匀性(可能会产生更多的碰撞)。

【讨论】:

  • 足够大的概率在实际使用中可以被认为是确定的。如果您考虑编写在程序生命周期内执行的概率为 1/1000000 的代码,您不妨避免外出,因为雷击事故的可能性是其两倍!
  • 如果您有几百万个文件要测试,在这种情况下发生冲突的几率可能并不像您想象的那么低(参见:preshing.com/20110504/hash-collision-probabilities)。示例:使用 32 位散列函数仅包含 77k 个文件时,几率高达 1/2!虽然使用 160 位甚至 64 位函数的可能性急剧下降,但我的观点是使用 CRC32 消除 99.99% 的情况可能更快,即使假设您需要一个较慢的哈希函数来处理少数情况,而不是通过为每个文件计算一个 160 位哈希函数来一次性完成所有工作。
  • CRC-32 适用于具有短突发错误或单比特错误的非常小的数据。它只有 32 位宽,并且比诸如 MurmurHash3(128 位)、SpookyHash(128 位)和 xxHash(64 位)等非加密哈希值慢。有更好、更快、更强大的选择.
【解决方案5】:

128 位确实足以检测不同的文件或块。碰撞的风险是微乎其微的,至少在没有故意碰撞的情况下是这样。

如果您要跟踪的文件或块的数量保持“足够小”(即不超过几百万个),64 位也可以证明足够好。

一旦确定了散列的大小,您需要一个具有一些非常好的分布属性的散列,例如在您的链接中以 Q.Score=10 列出的散列。

【讨论】:

    【解决方案6】:

    这有点取决于您将在一次迭代中计算的多少个哈希值。 例如,在计算 600 万个哈希时,64 位哈希的冲突概率为 1000000 分之一。

    参考:Hash collision probabilities

    【讨论】:

    • “计算 600 万个哈希值的概率为 100000 分之一”我认为你错过了一个零,实际概率会低 10 倍左右。
    • 一个有趣的情况是,当哈希输出是,例如 128b,> 64b,并且位是独立的,并且您屏蔽 64b 以用作键时。考虑到冲突可能发生在被屏蔽的位中(即不是获得的密钥的一部分)。直觉上,在这种情况下,我们似乎会有更好的概率。 (还没算过。)
    • 冲突是指哈希的所有位都匹配,所以如果你屏蔽掉一些仍然是冲突的位。不过,您可以在屏蔽时引入新的碰撞。不确定这种屏蔽有什么实际用途——你最终会花费 CPU 时间来计算你不会使用的位。
    【解决方案7】:

    查看MurmurHash2_160。它是对 MurmurHash2 的修改,可产生 160 位输出。

    它并行计算 MurmurHash2 的 5 个唯一结果并将它们彻底混合。根据摘要大小,冲突概率相当于 SHA-1。

    它仍然很快,但 MurmurHash3_128、SpookyHash128 和 MetroHash128 可能更快,尽管碰撞概率更高(但仍然不太可能)。还有 CityHash256 产生 256 位输出,应该也比 SHA-1 更快。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2013-09-12
      • 1970-01-01
      • 2014-04-18
      • 1970-01-01
      • 2012-04-30
      • 1970-01-01
      • 1970-01-01
      • 2010-11-16
      相关资源
      最近更新 更多