github.com/mtsmfm/go/src@v0.0.0-20221020090648-44bdcb9f8fde/math/rand/rand.go (about) 1 // Copyright 2009 The Go Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style 3 // license that can be found in the LICENSE file. 4 5 // Package rand implements pseudo-random number generators unsuitable for 6 // security-sensitive work. 7 // 8 // Random numbers are generated by a Source. Top-level functions, such as 9 // Float64 and Int, use a default shared Source that produces a deterministic 10 // sequence of values each time a program is run. Use the Seed function to 11 // initialize the default Source if different behavior is required for each run. 12 // The default Source is safe for concurrent use by multiple goroutines, but 13 // Sources created by NewSource are not. 14 // 15 // This package's outputs might be easily predictable regardless of how it's 16 // seeded. For random numbers suitable for security-sensitive work, see the 17 // crypto/rand package. 18 package rand 19 20 import "sync" 21 22 // A Source represents a source of uniformly-distributed 23 // pseudo-random int64 values in the range [0, 1<<63). 24 type Source interface { 25 Int63() int64 26 Seed(seed int64) 27 } 28 29 // A Source64 is a Source that can also generate 30 // uniformly-distributed pseudo-random uint64 values in 31 // the range [0, 1<<64) directly. 32 // If a Rand r's underlying Source s implements Source64, 33 // then r.Uint64 returns the result of one call to s.Uint64 34 // instead of making two calls to s.Int63. 35 type Source64 interface { 36 Source 37 Uint64() uint64 38 } 39 40 // NewSource returns a new pseudo-random Source seeded with the given value. 41 // Unlike the default Source used by top-level functions, this source is not 42 // safe for concurrent use by multiple goroutines. 43 // The returned Source implements Source64. 44 func NewSource(seed int64) Source { 45 return newSource(seed) 46 } 47 48 func newSource(seed int64) *rngSource { 49 var rng rngSource 50 rng.Seed(seed) 51 return &rng 52 } 53 54 // A Rand is a source of random numbers. 55 type Rand struct { 56 src Source 57 s64 Source64 // non-nil if src is source64 58 59 // readVal contains remainder of 63-bit integer used for bytes 60 // generation during most recent Read call. 61 // It is saved so next Read call can start where the previous 62 // one finished. 63 readVal int64 64 // readPos indicates the number of low-order bytes of readVal 65 // that are still valid. 66 readPos int8 67 } 68 69 // New returns a new Rand that uses random values from src 70 // to generate other random values. 71 func New(src Source) *Rand { 72 s64, _ := src.(Source64) 73 return &Rand{src: src, s64: s64} 74 } 75 76 // Seed uses the provided seed value to initialize the generator to a deterministic state. 77 // Seed should not be called concurrently with any other Rand method. 78 func (r *Rand) Seed(seed int64) { 79 if lk, ok := r.src.(*lockedSource); ok { 80 lk.seedPos(seed, &r.readPos) 81 return 82 } 83 84 r.src.Seed(seed) 85 r.readPos = 0 86 } 87 88 // Int63 returns a non-negative pseudo-random 63-bit integer as an int64. 89 func (r *Rand) Int63() int64 { return r.src.Int63() } 90 91 // Uint32 returns a pseudo-random 32-bit value as a uint32. 92 func (r *Rand) Uint32() uint32 { return uint32(r.Int63() >> 31) } 93 94 // Uint64 returns a pseudo-random 64-bit value as a uint64. 95 func (r *Rand) Uint64() uint64 { 96 if r.s64 != nil { 97 return r.s64.Uint64() 98 } 99 return uint64(r.Int63())>>31 | uint64(r.Int63())<<32 100 } 101 102 // Int31 returns a non-negative pseudo-random 31-bit integer as an int32. 103 func (r *Rand) Int31() int32 { return int32(r.Int63() >> 32) } 104 105 // Int returns a non-negative pseudo-random int. 106 func (r *Rand) Int() int { 107 u := uint(r.Int63()) 108 return int(u << 1 >> 1) // clear sign bit if int == int32 109 } 110 111 // Int63n returns, as an int64, a non-negative pseudo-random number in the half-open interval [0,n). 112 // It panics if n <= 0. 113 func (r *Rand) Int63n(n int64) int64 { 114 if n <= 0 { 115 panic("invalid argument to Int63n") 116 } 117 if n&(n-1) == 0 { // n is power of two, can mask 118 return r.Int63() & (n - 1) 119 } 120 max := int64((1 << 63) - 1 - (1<<63)%uint64(n)) 121 v := r.Int63() 122 for v > max { 123 v = r.Int63() 124 } 125 return v % n 126 } 127 128 // Int31n returns, as an int32, a non-negative pseudo-random number in the half-open interval [0,n). 129 // It panics if n <= 0. 130 func (r *Rand) Int31n(n int32) int32 { 131 if n <= 0 { 132 panic("invalid argument to Int31n") 133 } 134 if n&(n-1) == 0 { // n is power of two, can mask 135 return r.Int31() & (n - 1) 136 } 137 max := int32((1 << 31) - 1 - (1<<31)%uint32(n)) 138 v := r.Int31() 139 for v > max { 140 v = r.Int31() 141 } 142 return v % n 143 } 144 145 // int31n returns, as an int32, a non-negative pseudo-random number in the half-open interval [0,n). 146 // n must be > 0, but int31n does not check this; the caller must ensure it. 147 // int31n exists because Int31n is inefficient, but Go 1 compatibility 148 // requires that the stream of values produced by math/rand remain unchanged. 149 // int31n can thus only be used internally, by newly introduced APIs. 150 // 151 // For implementation details, see: 152 // https://lemire.me/blog/2016/06/27/a-fast-alternative-to-the-modulo-reduction 153 // https://lemire.me/blog/2016/06/30/fast-random-shuffling 154 func (r *Rand) int31n(n int32) int32 { 155 v := r.Uint32() 156 prod := uint64(v) * uint64(n) 157 low := uint32(prod) 158 if low < uint32(n) { 159 thresh := uint32(-n) % uint32(n) 160 for low < thresh { 161 v = r.Uint32() 162 prod = uint64(v) * uint64(n) 163 low = uint32(prod) 164 } 165 } 166 return int32(prod >> 32) 167 } 168 169 // Intn returns, as an int, a non-negative pseudo-random number in the half-open interval [0,n). 170 // It panics if n <= 0. 171 func (r *Rand) Intn(n int) int { 172 if n <= 0 { 173 panic("invalid argument to Intn") 174 } 175 if n <= 1<<31-1 { 176 return int(r.Int31n(int32(n))) 177 } 178 return int(r.Int63n(int64(n))) 179 } 180 181 // Float64 returns, as a float64, a pseudo-random number in the half-open interval [0.0,1.0). 182 func (r *Rand) Float64() float64 { 183 // A clearer, simpler implementation would be: 184 // return float64(r.Int63n(1<<53)) / (1<<53) 185 // However, Go 1 shipped with 186 // return float64(r.Int63()) / (1 << 63) 187 // and we want to preserve that value stream. 188 // 189 // There is one bug in the value stream: r.Int63() may be so close 190 // to 1<<63 that the division rounds up to 1.0, and we've guaranteed 191 // that the result is always less than 1.0. 192 // 193 // We tried to fix this by mapping 1.0 back to 0.0, but since float64 194 // values near 0 are much denser than near 1, mapping 1 to 0 caused 195 // a theoretically significant overshoot in the probability of returning 0. 196 // Instead of that, if we round up to 1, just try again. 197 // Getting 1 only happens 1/2⁵³ of the time, so most clients 198 // will not observe it anyway. 199 again: 200 f := float64(r.Int63()) / (1 << 63) 201 if f == 1 { 202 goto again // resample; this branch is taken O(never) 203 } 204 return f 205 } 206 207 // Float32 returns, as a float32, a pseudo-random number in the half-open interval [0.0,1.0). 208 func (r *Rand) Float32() float32 { 209 // Same rationale as in Float64: we want to preserve the Go 1 value 210 // stream except we want to fix it not to return 1.0 211 // This only happens 1/2²⁴ of the time (plus the 1/2⁵³ of the time in Float64). 212 again: 213 f := float32(r.Float64()) 214 if f == 1 { 215 goto again // resample; this branch is taken O(very rarely) 216 } 217 return f 218 } 219 220 // Perm returns, as a slice of n ints, a pseudo-random permutation of the integers 221 // in the half-open interval [0,n). 222 func (r *Rand) Perm(n int) []int { 223 m := make([]int, n) 224 // In the following loop, the iteration when i=0 always swaps m[0] with m[0]. 225 // A change to remove this useless iteration is to assign 1 to i in the init 226 // statement. But Perm also effects r. Making this change will affect 227 // the final state of r. So this change can't be made for compatibility 228 // reasons for Go 1. 229 for i := 0; i < n; i++ { 230 j := r.Intn(i + 1) 231 m[i] = m[j] 232 m[j] = i 233 } 234 return m 235 } 236 237 // Shuffle pseudo-randomizes the order of elements. 238 // n is the number of elements. Shuffle panics if n < 0. 239 // swap swaps the elements with indexes i and j. 240 func (r *Rand) Shuffle(n int, swap func(i, j int)) { 241 if n < 0 { 242 panic("invalid argument to Shuffle") 243 } 244 245 // Fisher-Yates shuffle: https://en.wikipedia.org/wiki/Fisher%E2%80%93Yates_shuffle 246 // Shuffle really ought not be called with n that doesn't fit in 32 bits. 247 // Not only will it take a very long time, but with 2³¹! possible permutations, 248 // there's no way that any PRNG can have a big enough internal state to 249 // generate even a minuscule percentage of the possible permutations. 250 // Nevertheless, the right API signature accepts an int n, so handle it as best we can. 251 i := n - 1 252 for ; i > 1<<31-1-1; i-- { 253 j := int(r.Int63n(int64(i + 1))) 254 swap(i, j) 255 } 256 for ; i > 0; i-- { 257 j := int(r.int31n(int32(i + 1))) 258 swap(i, j) 259 } 260 } 261 262 // Read generates len(p) random bytes and writes them into p. It 263 // always returns len(p) and a nil error. 264 // Read should not be called concurrently with any other Rand method. 265 func (r *Rand) Read(p []byte) (n int, err error) { 266 if lk, ok := r.src.(*lockedSource); ok { 267 return lk.read(p, &r.readVal, &r.readPos) 268 } 269 return read(p, r.src, &r.readVal, &r.readPos) 270 } 271 272 func read(p []byte, src Source, readVal *int64, readPos *int8) (n int, err error) { 273 pos := *readPos 274 val := *readVal 275 rng, _ := src.(*rngSource) 276 for n = 0; n < len(p); n++ { 277 if pos == 0 { 278 if rng != nil { 279 val = rng.Int63() 280 } else { 281 val = src.Int63() 282 } 283 pos = 7 284 } 285 p[n] = byte(val) 286 val >>= 8 287 pos-- 288 } 289 *readPos = pos 290 *readVal = val 291 return 292 } 293 294 /* 295 * Top-level convenience functions 296 */ 297 298 var globalRand = New(new(lockedSource)) 299 300 // Seed uses the provided seed value to initialize the default Source to a 301 // deterministic state. If Seed is not called, the generator behaves as 302 // if seeded by Seed(1). Seed values that have the same remainder when 303 // divided by 2³¹-1 generate the same pseudo-random sequence. 304 // Seed, unlike the Rand.Seed method, is safe for concurrent use. 305 func Seed(seed int64) { globalRand.Seed(seed) } 306 307 // Int63 returns a non-negative pseudo-random 63-bit integer as an int64 308 // from the default Source. 309 func Int63() int64 { return globalRand.Int63() } 310 311 // Uint32 returns a pseudo-random 32-bit value as a uint32 312 // from the default Source. 313 func Uint32() uint32 { return globalRand.Uint32() } 314 315 // Uint64 returns a pseudo-random 64-bit value as a uint64 316 // from the default Source. 317 func Uint64() uint64 { return globalRand.Uint64() } 318 319 // Int31 returns a non-negative pseudo-random 31-bit integer as an int32 320 // from the default Source. 321 func Int31() int32 { return globalRand.Int31() } 322 323 // Int returns a non-negative pseudo-random int from the default Source. 324 func Int() int { return globalRand.Int() } 325 326 // Int63n returns, as an int64, a non-negative pseudo-random number in the half-open interval [0,n) 327 // from the default Source. 328 // It panics if n <= 0. 329 func Int63n(n int64) int64 { return globalRand.Int63n(n) } 330 331 // Int31n returns, as an int32, a non-negative pseudo-random number in the half-open interval [0,n) 332 // from the default Source. 333 // It panics if n <= 0. 334 func Int31n(n int32) int32 { return globalRand.Int31n(n) } 335 336 // Intn returns, as an int, a non-negative pseudo-random number in the half-open interval [0,n) 337 // from the default Source. 338 // It panics if n <= 0. 339 func Intn(n int) int { return globalRand.Intn(n) } 340 341 // Float64 returns, as a float64, a pseudo-random number in the half-open interval [0.0,1.0) 342 // from the default Source. 343 func Float64() float64 { return globalRand.Float64() } 344 345 // Float32 returns, as a float32, a pseudo-random number in the half-open interval [0.0,1.0) 346 // from the default Source. 347 func Float32() float32 { return globalRand.Float32() } 348 349 // Perm returns, as a slice of n ints, a pseudo-random permutation of the integers 350 // in the half-open interval [0,n) from the default Source. 351 func Perm(n int) []int { return globalRand.Perm(n) } 352 353 // Shuffle pseudo-randomizes the order of elements using the default Source. 354 // n is the number of elements. Shuffle panics if n < 0. 355 // swap swaps the elements with indexes i and j. 356 func Shuffle(n int, swap func(i, j int)) { globalRand.Shuffle(n, swap) } 357 358 // Read generates len(p) random bytes from the default Source and 359 // writes them into p. It always returns len(p) and a nil error. 360 // Read, unlike the Rand.Read method, is safe for concurrent use. 361 func Read(p []byte) (n int, err error) { return globalRand.Read(p) } 362 363 // NormFloat64 returns a normally distributed float64 in the range 364 // [-math.MaxFloat64, +math.MaxFloat64] with 365 // standard normal distribution (mean = 0, stddev = 1) 366 // from the default Source. 367 // To produce a different normal distribution, callers can 368 // adjust the output using: 369 // 370 // sample = NormFloat64() * desiredStdDev + desiredMean 371 func NormFloat64() float64 { return globalRand.NormFloat64() } 372 373 // ExpFloat64 returns an exponentially distributed float64 in the range 374 // (0, +math.MaxFloat64] with an exponential distribution whose rate parameter 375 // (lambda) is 1 and whose mean is 1/lambda (1) from the default Source. 376 // To produce a distribution with a different rate parameter, 377 // callers can adjust the output using: 378 // 379 // sample = ExpFloat64() / desiredRateParameter 380 func ExpFloat64() float64 { return globalRand.ExpFloat64() } 381 382 type lockedSource struct { 383 lk sync.Mutex 384 s *rngSource // nil if not yet allocated 385 } 386 387 // source returns r.s, allocating and seeding it if needed. 388 // The caller must have locked r. 389 func (r *lockedSource) source() *rngSource { 390 if r.s == nil { 391 r.s = newSource(1) 392 } 393 return r.s 394 } 395 396 func (r *lockedSource) Int63() (n int64) { 397 r.lk.Lock() 398 n = r.source().Int63() 399 r.lk.Unlock() 400 return 401 } 402 403 func (r *lockedSource) Uint64() (n uint64) { 404 r.lk.Lock() 405 n = r.source().Uint64() 406 r.lk.Unlock() 407 return 408 } 409 410 func (r *lockedSource) Seed(seed int64) { 411 r.lk.Lock() 412 r.seed(seed) 413 r.lk.Unlock() 414 } 415 416 // seedPos implements Seed for a lockedSource without a race condition. 417 func (r *lockedSource) seedPos(seed int64, readPos *int8) { 418 r.lk.Lock() 419 r.seed(seed) 420 *readPos = 0 421 r.lk.Unlock() 422 } 423 424 // seed seeds the underlying source. 425 // The caller must have locked r.lk. 426 func (r *lockedSource) seed(seed int64) { 427 if r.s == nil { 428 r.s = newSource(seed) 429 } else { 430 r.s.Seed(seed) 431 } 432 } 433 434 // read implements Read for a lockedSource without a race condition. 435 func (r *lockedSource) read(p []byte, readVal *int64, readPos *int8) (n int, err error) { 436 r.lk.Lock() 437 n, err = read(p, r.source(), readVal, readPos) 438 r.lk.Unlock() 439 return 440 }