package rand
import "math/rand"
Package rand 实现了适用于模拟等任务的伪随机数生成器, 但不应用于安全敏感的工作。
随机数由 Source 生成,通常包装在 Rand 中。 这两种类型同一时间都应由单个 goroutine 使用:在多个 goroutine 之间共享需要某种形式的同步。
顶层函数,例如 Float64 和 Int, 可安全地由多个 goroutine 并发使用。
无论以何种方式设置种子,本包的输出都很容易被预测。
对于适用于安全敏感工作的随机数,请参见
crypto/rand 包。
This example shows the use of each of the methods on a *Rand.
The use of the global functions is the same, without the receiver.
Output:Example
package main
import (
"fmt"
"math/rand"
)
func main() {
answers := []string{
"It is certain",
"It is decidedly so",
"Without a doubt",
"Yes definitely",
"You may rely on it",
"As I see it yes",
"Most likely",
"Outlook good",
"Yes",
"Signs point to yes",
"Reply hazy try again",
"Ask again later",
"Better not tell you now",
"Cannot predict now",
"Concentrate and ask again",
"Don't count on it",
"My reply is no",
"My sources say no",
"Outlook not so good",
"Very doubtful",
}
fmt.Println("Magic 8-Ball says:", answers[rand.Intn(len(answers))])
}
Example (Rand)
package main
import (
"fmt"
"math/rand"
"os"
"text/tabwriter"
)
func main() {
// Create and seed the generator.
// Typically a non-fixed seed should be used, such as time.Now().UnixNano().
// Using a fixed seed will produce the same output on every run.
r := rand.New(rand.NewSource(99))
// The tabwriter here helps us generate aligned output.
w := tabwriter.NewWriter(os.Stdout, 1, 1, 1, ' ', 0)
defer w.Flush()
show := func(name string, v1, v2, v3 any) {
fmt.Fprintf(w, "%s\t%v\t%v\t%v\n", name, v1, v2, v3)
}
// Float32 and Float64 values are in [0, 1).
show("Float32", r.Float32(), r.Float32(), r.Float32())
show("Float64", r.Float64(), r.Float64(), r.Float64())
// ExpFloat64 values have an average of 1 but decay exponentially.
show("ExpFloat64", r.ExpFloat64(), r.ExpFloat64(), r.ExpFloat64())
// NormFloat64 values have an average of 0 and a standard deviation of 1.
show("NormFloat64", r.NormFloat64(), r.NormFloat64(), r.NormFloat64())
// Int31, Int63, and Uint32 generate values of the given width.
// The Int method (not shown) is like either Int31 or Int63
// depending on the size of 'int'.
show("Int31", r.Int31(), r.Int31(), r.Int31())
show("Int63", r.Int63(), r.Int63(), r.Int63())
show("Uint32", r.Uint32(), r.Uint32(), r.Uint32())
// Intn, Int31n, and Int63n limit their output to be < n.
// They do so more carefully than using r.Int()%n.
show("Intn(10)", r.Intn(10), r.Intn(10), r.Intn(10))
show("Int31n(10)", r.Int31n(10), r.Int31n(10), r.Int31n(10))
show("Int63n(10)", r.Int63n(10), r.Int63n(10), r.Int63n(10))
// Perm generates a random permutation of the numbers [0, n).
show("Perm", r.Perm(5), r.Perm(5), r.Perm(5))
}
Float32 0.2635776 0.6358173 0.6718283
Float64 0.628605430454327 0.4504798828572669 0.9562755949377957
ExpFloat64 0.3362240648200941 1.4256072328483647 0.24354758816173044
NormFloat64 0.17233959114940064 1.577014951434847 0.04259129641113857
Int31 1501292890 1486668269 182840835
Int63 3546343826724305832 5724354148158589552 5239846799706671610
Uint32 2760229429 296659907 1922395059
Intn(10) 1 2 5
Int31n(10) 4 7 8
Int63n(10) 7 6 3
Perm [1 4 2 3 0] [4 2 1 3 0] [1 2 4 0 3]
Index
- func ExpFloat64() float64
- func Float32() float32
- func Float64() float64
- func Int() int
- func Int31() int32
- func Int31n(n int32) int32
- func Int63() int64
- func Int63n(n int64) int64
- func Intn(n int) int
- func NormFloat64() float64
- func Perm(n int) []int
- func Read(p []byte) (n int, err error)
- func Seed(seed int64)
- func Shuffle(n int, swap func(i, j int))
- func Uint32() uint32
- func Uint64() uint64
-
type Rand
- func New(src Source) *Rand
- func (r *Rand) ExpFloat64() float64
- func (r *Rand) Float32() float32
- func (r *Rand) Float64() float64
- func (r *Rand) Int() int
- func (r *Rand) Int31() int32
- func (r *Rand) Int31n(n int32) int32
- func (r *Rand) Int63() int64
- func (r *Rand) Int63n(n int64) int64
- func (r *Rand) Intn(n int) int
- func (r *Rand) NormFloat64() float64
- func (r *Rand) Perm(n int) []int
- func (r *Rand) Read(p []byte) (n int, err error)
- func (r *Rand) Seed(seed int64)
- func (r *Rand) Shuffle(n int, swap func(i, j int))
- func (r *Rand) Uint32() uint32
- func (r *Rand) Uint64() uint64
- type Source
- type Source64
- type Zipf
Examples
Functions
func ExpFloat64
func ExpFloat64() float64
ExpFloat64 从默认 Source 返回一个在范围 (0, +[math.MaxFloat64]] 内服从指数分布的 float64,其速率参数 (lambda) 为 1,均值为 1/lambda (1)。 要产生具有不同速率参数的分布, 调用者可以使用以下方式调整输出:
sample = ExpFloat64() / desiredRateParameter
func Float32
func Float32() float32
Float32 从默认 Source 以 float32 返回半开区间 [0.0,1.0) 内的 一个伪随机数。
func Float64
func Float64() float64
Float64 从默认 Source 以 float64 返回半开区间 [0.0,1.0) 内的 一个伪随机数。
func Int
func Int() int
Int 从默认 Source 返回一个非负的伪随机 int。
func Int31
func Int31() int32
Int31 从默认 Source 以 int32 返回一个 非负的伪随机 31 位整数。
func Int31n
func Int31n(n int32) int32
Int31n 从默认 Source 以 int32 返回半开区间 [0,n) 内的 一个非负伪随机数。 如果 n <= 0,它会 panic。
func Int63
func Int63() int64
Int63 从默认 Source 以 int64 返回一个 非负的伪随机 63 位整数。
func Int63n
func Int63n(n int64) int64
Int63n 从默认 Source 以 int64 返回半开区间 [0,n) 内的 一个非负伪随机数。 如果 n <= 0,它会 panic。
func Intn
func Intn(n int) int
Intn 从默认 Source 以 int 返回半开区间 [0,n) 内的
一个非负伪随机数。
如果 n <= 0,它会 panic。
Example
package main
import (
"fmt"
"math/rand"
)
func main() {
fmt.Println(rand.Intn(100))
fmt.Println(rand.Intn(100))
fmt.Println(rand.Intn(100))
}
func NormFloat64
func NormFloat64() float64
NormFloat64 从默认 Source 返回一个在范围 [-math.MaxFloat64, +[math.MaxFloat64]] 内服从 标准正态分布(均值 = 0,标准差 = 1)的 float64。 要产生不同的正态分布,调用者可以使用以下方式 调整输出:
sample = NormFloat64() * desiredStdDev + desiredMean
func Perm
func Perm(n int) []int
Perm 从默认 Source 以 n 个 int 的切片形式返回半开区间 [0,n) 内
整数的一个伪随机排列。
Output:Example
package main
import (
"fmt"
"math/rand"
)
func main() {
for _, value := range rand.Perm(3) {
fmt.Println(value)
}
}
1
2
0
func Read
func Read(p []byte) (n int, err error)
Read 从默认 Source 生成 len(p) 个随机字节,并将它们 写入 p。它总是返回 len(p) 和一个 nil 错误。 与 Rand.Read 方法不同,Read 可安全地并发使用。
已弃用:对于几乎所有用例,crypto/rand.Read 都更合适。 如果需要确定性的 source,请使用 math/rand/v2.ChaCha8.Read。
func Seed
func Seed(seed int64)
Seed 使用提供的种子值将默认 Source 初始化为 确定性的状态。除以 2³¹-1 后余数相同的种子值 会生成相同的伪随机序列。 与 Rand.Seed 方法不同,Seed 可安全地并发使用。
如果未调用 Seed,生成器会在程序启动时随机播种。
在 Go 1.20 之前,生成器在程序启动时会像 Seed(1) 那样播种。 要强制使用旧行为,请在程序启动时调用 Seed(1)。 或者,在调用本包中的任何函数之前, 在环境中设置 GODEBUG=randautoseed=0。
已弃用:从 Go 1.20 起,没有理由用随机值调用 Seed。 那些用已知值调用 Seed 以获得特定结果序列的程序 应使用 New(NewSource(seed)) 来获得 一个本地随机生成器。
从 Go 1.24 起 Seed 是无操作。要恢复先前的行为, 请设置 GODEBUG=randseednop=0。
func Shuffle
func Shuffle(n int, swap func(i, j int))
Shuffle 使用默认 Source 对元素的顺序进行伪随机化。
n 是元素的数量。如果 n < 0,Shuffle 会 panic。
swap 交换索引为 i 和 j 的元素。
Example
package main
import (
"fmt"
"math/rand"
"strings"
)
func main() {
words := strings.Fields("ink runs from the corners of my mouth")
rand.Shuffle(len(words), func(i, j int) {
words[i], words[j] = words[j], words[i]
})
fmt.Println(words)
}
Example (SlicesInUnison)
package main
import (
"fmt"
"math/rand"
)
func main() {
numbers := []byte("12345")
letters := []byte("ABCDE")
// Shuffle numbers, swapping corresponding entries in letters at the same time.
rand.Shuffle(len(numbers), func(i, j int) {
numbers[i], numbers[j] = numbers[j], numbers[i]
letters[i], letters[j] = letters[j], letters[i]
})
for i := range numbers {
fmt.Printf("%c: %c\n", letters[i], numbers[i])
}
}
func Uint32
func Uint32() uint32
Uint32 从默认 Source 以 uint32 返回一个 伪随机 32 位值。
func Uint64
func Uint64() uint64
Uint64 从默认 Source 以 uint64 返回一个 伪随机 64 位值。
Types
type Rand
type Rand struct { // contains filtered or unexported fields }
Rand 是一个随机数来源。
func New
func New(src Source) *Rand
New 返回一个新的 Rand,它使用来自 src 的随机值 来生成其他随机值。
func (*Rand) ExpFloat64
func (r *Rand) ExpFloat64() float64
ExpFloat64 返回一个在范围 (0, +[math.MaxFloat64]] 内服从指数分布的 float64,其速率参数 (lambda) 为 1,均值为 1/lambda (1)。 要产生具有不同速率参数的分布, 调用者可以使用以下方式调整输出:
sample = ExpFloat64() / desiredRateParameter
func (*Rand) Float32
func (r *Rand) Float32() float32
Float32 以 float32 返回半开区间 [0.0,1.0) 内的一个伪随机数。
func (*Rand) Float64
func (r *Rand) Float64() float64
Float64 以 float64 返回半开区间 [0.0,1.0) 内的一个伪随机数。
func (*Rand) Int
func (r *Rand) Int() int
Int 返回一个非负的伪随机 int。
func (*Rand) Int31
func (r *Rand) Int31() int32
Int31 以 int32 返回一个非负的伪随机 31 位整数。
func (*Rand) Int31n
func (r *Rand) Int31n(n int32) int32
Int31n 以 int32 返回半开区间 [0,n) 内的一个非负伪随机数。 如果 n <= 0,它会 panic。
func (*Rand) Int63
func (r *Rand) Int63() int64
Int63 以 int64 返回一个非负的伪随机 63 位整数。
func (*Rand) Int63n
func (r *Rand) Int63n(n int64) int64
Int63n 以 int64 返回半开区间 [0,n) 内的一个非负伪随机数。 如果 n <= 0,它会 panic。
func (*Rand) Intn
func (r *Rand) Intn(n int) int
Intn 以 int 返回半开区间 [0,n) 内的一个非负伪随机数。 如果 n <= 0,它会 panic。
func (*Rand) NormFloat64
func (r *Rand) NormFloat64() float64
NormFloat64 返回一个在 范围 -math.MaxFloat64 到 +[math.MaxFloat64](含两端)内, 服从标准正态分布(均值 = 0,标准差 = 1)的 float64。 要产生不同的正态分布,调用者可以使用以下方式 调整输出:
sample = NormFloat64() * desiredStdDev + desiredMean
func (*Rand) Perm
func (r *Rand) Perm(n int) []int
Perm 以 n 个 int 的切片形式返回半开区间 [0,n) 内 整数的一个伪随机排列。
func (*Rand) Read
func (r *Rand) Read(p []byte) (n int, err error)
Read 生成 len(p) 个随机字节并将它们写入 p。它 总是返回 len(p) 和一个 nil 错误。 Read 不应与任何其他 Rand 方法并发调用。
func (*Rand) Seed
func (r *Rand) Seed(seed int64)
Seed 使用提供的种子值将生成器初始化为确定性的状态。 Seed 不应与任何其他 Rand 方法并发调用。
func (*Rand) Shuffle
func (r *Rand) Shuffle(n int, swap func(i, j int))
Shuffle 对元素的顺序进行伪随机化。 n 是元素的数量。如果 n < 0,Shuffle 会 panic。 swap 交换索引为 i 和 j 的元素。
func (*Rand) Uint32
func (r *Rand) Uint32() uint32
Uint32 以 uint32 返回一个伪随机 32 位值。
func (*Rand) Uint64
func (r *Rand) Uint64() uint64
Uint64 以 uint64 返回一个伪随机 64 位值。
type Source
type Source interface { Int63() int64 Seed(seed int64) }
Source 表示一个在范围 [0, 1<<63) 内的均匀分布 伪随机 int64 值的来源。
Source 不能安全地由多个 goroutine 并发使用。
func NewSource
func NewSource(seed int64) Source
NewSource 返回一个用给定值播种的新的伪随机 Source。 与顶层函数使用的默认 Source 不同,此 source 不能安全地 由多个 goroutine 并发使用。 返回的 Source 实现了 Source64。
type Source64
type Source64 interface { Source Uint64() uint64 }
Source64 是一种 Source,它还可以直接在 范围 [0, 1<<64) 内生成均匀分布的伪随机 uint64 值。 如果 Rand r 的底层 Source s 实现了 Source64, 那么 r.Uint64 会返回一次调用 s.Uint64 的结果, 而不是调用两次 s.Int63。
type Zipf
type Zipf struct { // contains filtered or unexported fields }
Zipf 生成服从 Zipf 分布的变量。
func NewZipf
func NewZipf(r *Rand, s float64, v float64, imax uint64) *Zipf
NewZipf 返回一个 Zipf 变量生成器。 该生成器生成值 k ∈ [0, imax], 使得 P(k) 与 (v + k) ** (-s) 成正比。 要求:s > 1 且 v >= 1。
func (*Zipf) Uint64
func (z *Zipf) Uint64() uint64
Uint64 返回一个从 Zipf 对象所描述的 Zipf 分布中抽取的值。
Directories
| v2 | Package rand 实现了适用于模拟等任务的伪随机数生成器, 但不应用于安全敏感的工作。 |