如何在官方围棋之旅中播种随机数生成器?

How do I Seed random number generator on official Tour of Go?

Go官方游给出沙盒中代码如下:

package main

import (
    "fmt"
    "math/rand"
)

func main() {
    fmt.Println("My favorite number is", rand.Intn(10))
}

这条指令:

Note: the environment in which these programs are executed is deterministic, so each time you run the example program rand.Intn will return the same number. (To see a different number, seed the number generator; see rand.Seed.)

阅读rand.Seed and reading this answer官方文档下的条目后,我仍然无法正确设置随机数生成器的种子。

有人可以演示如何使用 rand.Seed 函数为随机数生成器设置种子吗?

非常感谢, 乔恩

默认情况下 rand.Intn 使用 globalRand.Intn. Its created internally, refer here. So when you set via rand.Seed

rand.Seed(time.Now().UTC().UnixNano())

然后 globalRand 使用新的种子值。

如果需要,您可以使用种子值创建自己的随机数生成器。参考godoc example.


播放Link(无种子):https://play.golang.org/p/2yg7xjvHoJ

输出:

My favorite number is 1
My favorite number is 7
My favorite number is 7
My favorite number is 9
My favorite number is 1
My favorite number is 8
My favorite number is 5
My favorite number is 0
My favorite number is 6

播放 Link(带种子):https://play.golang.org/p/EpW6R5rvM4

输出:

My favorite number is 0
My favorite number is 8
My favorite number is 7
My favorite number is 2
My favorite number is 3
My favorite number is 9
My favorite number is 4
My favorite number is 7
My favorite number is 8

编辑:

正如@AlexanderTrakhimenok 提到的,在 playground 中程序执行是 deterministic。但是,playground 不会阻止您提供 rand.Seed 值。

记住种子值为 int64

当您 rand.Intn 时,它使用 globalRand 的默认种子值 1

var globalRand = New(&lockedSource{src: NewSource(1).(Source64)})

并且在 playground 中 time.Now().UTC().UnixNano() 为您提供与 the start time is locked to a constant 相同的值 1257894000000000000。但它与默认种子值不同,这就是为什么第二个操场 link 产生不同的结果

所以上面两个总是会产生相同的结果。

我们应该如何改变操场上的结果?

是的,我们可以。让我们将 UnixNano()1500909006430687579 提供给 rand.Seed,这是从我的机器生成的。

播放 Link: https://play.golang.org/p/-nTydej8YF

输出:

My favorite number is 3
My favorite number is 5
My favorite number is 3
My favorite number is 8
My favorite number is 0
My favorite number is 5
My favorite number is 4
My favorite number is 7
My favorite number is 1

正如你自己所说:

the environment in which these programs are executed is deterministic.

因此 Go Playground 的设计不允许创建真正的伪随机输出。

这样做是为了缓存结果,以尽量减少 CPU/memory 对后续 运行 的使用。因此引擎可以只对您的程序进行一次评估,并且每次您或其他任何人再次 运行 时都提供相同的缓存输出。

出于同样的目的,开始时间被锁定为一个常数。

您可能想阅读一篇博客 post,了解如何以及为何以这种方式实施:https://blog.golang.org/playground