在 rabin-karp 滚动哈希中选择基数和模素数

Posted

技术标签:

【中文标题】在 rabin-karp 滚动哈希中选择基数和模素数【英文标题】:Choosing radix and modulus prime in rabin-karp rolling hash 【发布时间】:2014-01-29 16:05:48 【问题描述】:

哈希函数在Wikipedia上解释

它说,“a 和 n 的选择对于获得良好的散列至关重要;”并指的是感觉不相关的线性同余生成器文章。我无法弄清楚这些值是如何选择的。有什么建议吗?

【问题讨论】:

真的没有秘诀。您必须进行试验,或使用其他人已经证明在一般情况下或特定情况下工作良好的方法。 【参考方案1】:

该算法的基础是一个非零次数的多项式至多d有至多d个零。每个长度-k 字符串都有自己关联的次数为 k - 1 的多项式,我们通过减去相关字符串的多项式并在 一个。如果字符串相等,则结果始终为零。如果字符串不相等,则结果为零当且仅当 a 是多项式差的零之一(这是将素数要求放在 n em>,因为整数 mod n 否则不会是一个字段)。

至少在理论上,我们希望 a 是随机的,这样不经意的对手就不会以任何频率制造误报。如果我们没有预料到麻烦,那么选择 a 可能会更好,这样乘以 a 就很便宜(例如,a em> 有少量的一位)。然而,一些选择在典型的字符串集上是不好的(例如,a = 1)。我们希望 n 足够大,以避免随机出现误报(概率 (k - 1)/n),但又足够小并且最好的特殊形式,以便模计算是有效的。

【讨论】:

你能提供一些很好选择的例子吗? (模数) @Learningstatsbyexample 2^31-1 是许多应用程序的不错选择。您可以使用 64 位算术可移植地进行乘法运算,并且可以优化模运算以避免除法(并且您的编译器可能能够为您执行此操作,例如,我的笔记本电脑上的 clang 发出没有除法运算的汇编代码)。 Rabin Karp 优化所需的逆模不会溢出吗? @Learningstatsbyexample 逆模是一个介于 1 和 n-1 之间的数字,所以我不确定为什么会发生这种情况。 好的,我发现了问题。如果 p 这么高,您的滚动哈希中可能会出现负数。所以缩放 p (或 p ** base 的最大值)youtu.be/w6nuXg0BISo?t=1984 是有意义的

以上是关于在 rabin-karp 滚动哈希中选择基数和模素数的主要内容,如果未能解决你的问题,请参考以下文章

模式匹配:滚动哈希到 Rabin-Karp 算法

模式匹配:滚动哈希到 Rabin-Karp 算法

Rabin-Karp ACM训练

Rabin-Karp算法代码中的负哈希值

字符串哈希之Rabin-Karp,poj1200

在滚动散列中,散列函数的除法方法中使用的素数与为数字选择的基数之间的关系是啥?