Scala Murnhash3库与Python mmh3库不匹配

2024-06-02 07:57:33 发布

您现在位置:Python中文网/ 问答频道 /正文

我需要在Python和Scala中杂音散列字符串。然而,他们给出了截然不同的结果。Scala的内置库MurmurHash3似乎没有提供与我尝试过的任何其他库相同的结果。奇怪的是它似乎只匹配一个字符而不是多个字符。以下是一些示例:

Python:

mmh3.hash('string', 0)
res: -1390314837

斯卡拉:

^{pr2}$

我尝试过使用有符号和无符号int,因为我知道Java已经签名了,而python正在包装的C实现使用的是unsigned。但即使使用NumPy转换成有符号int也没有帮助。这个网站似乎同意python的实现:

http://murmurhash.shorelabs.com/

有什么想法吗?在


Tags: 字符串示例string符号reshash杂音java
2条回答

这是由于Scala的MurmurHash3.stringHashMurmurHash3.bytesHash在实现上的差异造成的

MurmurHash3.bytesHash和python的mmh3.hash将字符以4个一组的形式传递给哈希混合器,但是MurmurHash3.stringHash将字符以2个为一组进行混合。这意味着两个哈希函数返回完全不同的输出:

import scala.util.hashing.MurmurHash3

val testString = "FiddlyString"

MurmurHash3.stringHash(testString)           /* Returns an int */
MurmurHash3.bytesHash(testString.getBytes()) /* Returns a different int */

因此,如果您需要python和Scala的MurmurHash3值的结果来精确匹配:

我建议第一个选项,特别是当您的用例需要更好的性能,或者您需要散列大量字符串时

Scala使用编码为UTF-16的Java字符串。它们一次打包成Int;Python使用char*(8位),因此一次打包为四个字符,而不是两个字符。在

Edit:Scala还按MSB顺序打包字符,即(s.charAt(i) << 16) | (s.charAt(i+1))。如果要得到完全相同的答案真的很重要的话,你可能需要切换到一系列的空头,然后交换每一对。(或者将Scala代码移植到Python,反之亦然)它还以字符串长度结束;我不确定Python是如何合并长度数据的,如果它有。(这一点很重要,因此可以区分字符串"\u0000"和{}。)

相关问题 更多 >