Hash 如何在连接2个字符串后快速生成新的字符串哈希

Hash 如何在连接2个字符串后快速生成新的字符串哈希,hash,string-concatenation,Hash,String Concatenation,如果我的数学是正确的,那么如果我已经有了每个字符串的散列值,我可以为两个字符串的串联快速生成一个新的散列值。但仅当哈希函数的形式为: hash(n) = k * hash(n-1) + c(n), and h(0) = 0. 在这种情况下, hash( concat(s1,s2) ) = k**length(s2) * hash(s1) + hash(s2) 例如 现在,对于SDBM散列k=65599。而DJB散列具有k=33(或者可能是31?)和h(0)=5381,因此,要使其工作,您可以

如果我的数学是正确的,那么如果我已经有了每个字符串的散列值,我可以为两个字符串的串联快速生成一个新的散列值。但仅当哈希函数的形式为:

hash(n) = k * hash(n-1) + c(n), and h(0) = 0.
在这种情况下,

hash( concat(s1,s2) ) = k**length(s2) * hash(s1) + hash(s2)
例如

现在,对于
SDBM散列
k=65599
。而
DJB散列
具有
k=33
(或者可能是
31
?)和
h(0)=5381
,因此,要使其工作,您可以设置
h(0)=0

但是对
DJB散列的修改使用
xor
而不是
+
来添加每个字符


如果哈希函数使用
xor
而不是
+
,是否有另一种技术可以快速计算连接字符串的哈希值?

如果第二个哈希函数是哈希初始状态的函数,则该技术是正确的。对于某些类型的散列函数,很容易根据新的初始状态(如xor'e字或它们的和等)来移动它们。但在一般情况下,这几乎是不可能的(在另一种情况下,在密码匹配中使用hash+“salt”将更容易被破解)

但通常您可以使用第一个字符串的哈希结果,然后继续从第二个字符串馈送数据

更新:
我想没有办法找到f(x,y)

h_abc = hashOf(h0, "abc")  
h_def = hashOf(h0, "def")  
(h_abcdef = f(h_abc, h_def)) == hashOf(h0, "abcdef")  
但你可以:

h_abc = hashOf(h1, "abc")  
(h_abcdef = hashOf(h_abc, "def")) == hashOf(h0, "abcdef")  
你不能这么做的原因之一是“33”不是“2”的幂。如果将使用“32”(2**5),则:


h_abcdef==(h_abc我想你是说一般情况是从第一个字符串的散列开始,并将其视为h(0)然后输入第二个字符串的每个字符以生成新的散列。@philcolbourn,只要不要删除为第一个字符串计算散列的Intermediate对象,您就可以继续更新该对象以获得两个字符串的散列。我看到的散列函数的大多数接口在生成散列r后都可以继续进行esult用于已馈送的数据。在这些情况下,我的中间对象是散列值,但是否有使用
xor
的乘法散列的神奇公式?请注意我的期望,但您已经回答了这个问题。我认为len(abc)应该是len(def),但在您的示例中,这并不重要,因为两者都是3。
h_abc = hashOf(h1, "abc")  
(h_abcdef = hashOf(h_abc, "def")) == hashOf(h0, "abcdef")  
h_abcdef == (h_abc << (5*len(abc))) xor h_def