如何在Go中生成字符串的哈希值?

MrR*_*ROY 31 hash go

例如:

hash("HelloWorld") = 1234567
Run Code Online (Sandbox Code Playgroud)

有没有内置功能可以做到这一点?

谢谢.

zzz*_*zzz 69

包是这很有帮助.请注意,它是对特定哈希实现的抽象.在包子目录中找到一些现成的.

例:

package main

import (
        "fmt"
        "hash/fnv"
)

func hash(s string) uint32 {
        h := fnv.New32a()
        h.Write([]byte(s))
        return h.Sum32()
}

func main() {
        fmt.Println(hash("HelloWorld"))
        fmt.Println(hash("HelloWorld."))
}
Run Code Online (Sandbox Code Playgroud)

(还在这里)


输出:

926844193
107706013
Run Code Online (Sandbox Code Playgroud)

  • 这些散列不是很独特。两个不同的字符串匹配同一个 uint32 的几率大约为 1 到 40 亿。我不会将它用于唯一性。这是一个可能证明更有用的示例:每个任务都有一个唯一的“字符串”,我想在 50 个队列之间均匀分配任务。我会做(使用上述函数)hash("HelloWorld") % 50。 (3认同)
  • 此外,可以使用单个实例和`Write` /`Reset`,而不是每次都创建`New32a`.我不知道它的价格是多少.例如:https://play.golang.org/p/aUeNBo755g (2认同)
  • @iwind 每个进入较小空间的哈希函数(例如此处进入 uint32 的任意长度字符串)都保证会发生冲突,因此“我发现一个特定的冲突”并不是判断方法好坏的论据。如果您分析该方法并发现高碰撞率或不均匀分布或其他一些有意义的缺陷,这将是一个令人信服的论点,但我想 FNV 已经存在这样的分析。 (2认同)
  • @IvanBlack 我想知道在每次调用 getHash 时使用相同的 New32a 实例时的并发和竞争条件问题。在我看来,两个同时进行的 getHash 函数调用可能会以某种方式交错,导致其中一个在执行 Sum 调用之前重置另一个的 Write,从而给出您不想要的结果。 (2认同)

Rae*_*ali 5

这是一个可用于生成哈希数的函数:

// FNV32a hashes using fnv32a algorithm
func FNV32a(text string) uint32 {
    algorithm := fnv.New32a()
    algorithm.Write([]byte(text))
    return algorithm.Sum32()
}
Run Code Online (Sandbox Code Playgroud)

我在这里整理了一组这些实用程序哈希函数:https : //github.com/shomali11/util

你会发现FNV32, FNV32a, FNV64, FNV64a, MD5, SHA1,SHA256SHA512