Golang基于时间戳生成随机数的方法

Golang基于时间戳生成随机数的方法 大家好,

我想基于时间戳生成随机数。有人能在这方面提供帮助吗?我一直在尝试使用 math/rand 包,但没有得到预期的输出。

我希望基于时间戳生成一个8位随机数。如果有人能帮忙,提供任何参考示例将对我有很大帮助。

package main

import "fmt"
import "math/rand"

func main() {

    k1 := rand.Intn(30)
    fmt.Println(k1)
}
14 回复

请随意使用我的 token 包 😎

更多关于Golang基于时间戳生成随机数的方法的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html


非常感谢,这让我理解得更透彻了。

如果你想要真正唯一的东西,直接使用 UUID 即可。

不过除此之外,@jayts 的方法应该也足够了,它能在实际机器上提供合理的熵值。

你好 Nobbz,是的,我想要非常独特的标识符。因为我需要将其用作其他用途的键值。请问你有关于 UUID 的示例吗?

虽然手头没有现成的,而且也不是用Golang实现的。但既然这些功能非常常见,我相信肯定有现成的包可以使用。

8位十进制、十六进制、八进制还是二进制数字?

时间戳是以什么方式生成的?如果随机数生成器再次输入相同的时间戳,它是否应该给出与之前相同的数字?这与直接使用随机数生成器有何不同?或者您实际上需要将时间作为种子,并希望根据给定时间戳生成相同的随机值序列?

你好Jayts,如果我的问题表述不够清晰,我表示歉意。

实际上,我想实现的是:每次程序被调用时,生成一个唯一的随机数。我认为唯一可行的方法是借助时间戳乘以rand.Intn来实现,但未能成功实施。我尝试过使用rand.Intn(30)乘以time。

希望你能在这方面给予帮助。如果我的问题仍然不够明确,请务必告知。

请注意,该代码库因不活跃和已知问题未得到修复而被标记(参见此问题)。社区已将其分叉并在新地址进行维护。

奇怪的是,原代码库在几天前出现了新的提交,但在此之前自四月份起就一直没有活动记录。

GitHub

头像

satori/go.uuid

Go语言的UUID包。通过在GitHub上创建账户来为satori/go.uuid开发做贡献。

这是一个流行的Go语言UUID包。

Dattatray_Jadhav:

这正是我在寻找的解决方案。 只是有一个疑问,能否请您解释一下为什么使用以下语句: if rn > 10000000 { break }

您说过需要8位数字。该语句检查数字是否大于10000000以确保它有8位数,如果数字太小则会重新尝试。实际上,我应该使用 >=

我不确定是否理解了您的意思。您可以使用我展示的代码,只需生成一个随机数而不是20个。只要time.Now()正常工作,每次运行程序都会得到不同的随机数。(只是不要在Go Playground或其他模拟环境中期望良好的行为。)

以下代码对您来说有什么不能用的原因吗?

package main

import (
        "fmt"
        "math/rand"
        "time"
)

func main() {
        var rn int

        for {
                rn = rand.New(rand.NewSource(time.Now().UnixNano())).Int() % 100000000
                if rn > 10000000 { break }
        }
        fmt.Printf("%d\n", rn)
}

非常感谢jayts。这正是我一直在寻找的。

只是有个疑问想请教一下。能否请您解释一下为什么使用了下面这条语句: if rn > 10000000 { break }

您能更详细地说明一下这个条件判断的作用吗?

我也不太理解这个问题,但也许这就是你想要的,或者类似的东西。
函数 srandom() 基于当前系统时钟初始化随机数生成器。之后,你可以调用 random() 来获取一个随机的 int。(它的设计意图是模仿 C 标准库中的 srandom()random() 函数。)

这个程序会生成恰好为 8 位十进制数的随机整数,不会更少。

请小心并测试它。在某些虚拟化环境中(例如 Go Playground),随机数生成器每次都会以相同的方式初始化,因此总是生成相同的随机数序列。

package main

import (
        "fmt"
        "math/rand"
        "time"
)

var randomgen *rand.Rand

func srandom() {
        randomgen = rand.New(rand.NewSource(time.Now().UnixNano()))
}

func random() int {
        return randomgen.Int()
}

func main() {
        var rn int

        srandom()    // initialize random number generator

        for i := 0; i < 20; i++ {
                for {
                        rn = random() % 100000000
                        if rn > 10000000 { break }
                }
                fmt.Printf("%d\n", rn)
        }

}

在Go语言中,基于时间戳生成随机数需要将时间戳作为随机数生成器的种子。这样可以确保每次程序运行时,如果时间戳不同,生成的随机数序列也会不同。以下是一个示例代码,展示如何基于当前时间戳生成一个8位随机数(范围从10000000到99999999):

package main

import (
    "fmt"
    "math/rand"
    "time"
)

func main() {
    // 使用当前时间戳作为随机数生成器的种子
    rand.Seed(time.Now().UnixNano())
    
    // 生成一个8位随机数(10000000 到 99999999)
    randomNum := rand.Intn(90000000) + 10000000
    fmt.Println(randomNum)
}

在这个示例中:

  • time.Now().UnixNano() 获取当前时间的纳秒级时间戳,确保种子值的高精度。
  • rand.Seed() 使用该时间戳初始化随机数生成器。
  • rand.Intn(90000000) 生成一个0到89999999之间的随机整数,然后加上10000000,确保结果在10000000到99999999之间,形成一个8位数字。

如果你需要一个固定长度的8位数字(包括前导零的情况),可以使用以下方法:

package main

import (
    "fmt"
    "math/rand"
    "time"
)

func main() {
    rand.Seed(time.Now().UnixNano())
    
    // 生成0到99999999之间的随机数,格式化为8位数字(前导零)
    randomNum := rand.Intn(100000000)
    formattedNum := fmt.Sprintf("%08d", randomNum)
    fmt.Println(formattedNum)
}

这里使用 fmt.Sprintf("%08d", randomNum) 将数字格式化为8位,不足部分用前导零填充。例如,如果生成的数字是123,输出将是"00000123"。

确保每次运行程序时使用不同的时间戳种子,以避免生成相同的随机数序列。

回到顶部