duan198299 2018-01-17 17:48
浏览 440
已采纳

如何在Golang中使用字符串作为rand.Seed()函数的输入?

What I want to do:

Based on the contents of a string (like a1b2c3d4e5, for example), I want to generate a bunch of "repeatable" random events. Generating repeatable random numbers in Golang is easy - you just seed the random number generator with a specific number using the rand.Seed() function, and then you are done.

However, the rand.Seed() function takes an int64 as an argument. So I will need to convert a string to a int64 somehow.

What I tried already:

My first thought was to encode the string using base64, and then convert the sequence of bytes to a int64. However, through some basic testing that only seems to support strings of around 7 length. After I add an 8th character, the number just stays the same.

I guess the fundamental problem here is that there are more possible string values than there are possible int64 values.

So what about some kind of hash function? Most hash functions that I know of return a sequence of bytes; I would need some kind of hash function that returns an int64. Perhaps this approach is also misguided?

  • 写回答

2条回答 默认 最新

  • douyin4875 2018-01-17 17:54
    关注

    A hash of the string will do the trick.

    You can use:

    • md5 sum of the string (returns 16 bytes)
    • convert the first 8 bytes into a uint64 (binary.BigEndian.Uint64 ignores the rest. It will crash if your input is less than 8 bytes though).

    Sample code (playground link):

    package main
    
    import (
        "crypto/md5"
        "encoding/binary"
        "fmt"
        "io"
        "math/rand"
    )
    
    func main() {
        h := md5.New()
        io.WriteString(h, "And Leon's getting larger!")
        var seed uint64 = binary.BigEndian.Uint64(h.Sum(nil))
        fmt.Println(seed)
        rand.Seed(int64(seed))
        fmt.Println(rand.Int())
    }
    

    Prints:

    2458341265858962012
    792667671
    

    Note: md5 is just an example. You can use any hash that generates at least 8 bytes. eg: sha256. Simply replace md5.New() with sha256.New() (and the import). You can find a nice list of hash examples here.

    And a big word of warning: this does not talk about crypto applications at all. I'm assuming this is for something like a user-provided seed (eg: a game seed) for non-crypto purposes.

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论
查看更多回答(1条)

报告相同问题?

悬赏问题

  • ¥15 很想要一个很好的答案或提示
  • ¥15 扫描项目中发现AndroidOS.Agent、Android/SmsThief.LI!tr
  • ¥15 怀疑手机被监控,请问怎么解决和防止
  • ¥15 Qt下使用tcp获取数据的详细操作
  • ¥15 idea右下角设置编码是灰色的
  • ¥15 全志H618ROM新增分区
  • ¥15 在grasshopper里DrawViewportWires更改预览后,禁用电池仍然显示
  • ¥15 NAO机器人的录音程序保存问题
  • ¥15 C#读写EXCEL文件,不同编译
  • ¥15 MapReduce结果输出到HBase,一直连接不上MySQL