cpython / Lib / whrandom.py

 ``` 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144``` ```"""Wichman-Hill random number generator. Wichmann, B. A. & Hill, I. D. (1982) Algorithm AS 183: An efficient and portable pseudo-random number generator Applied Statistics 31 (1982) 188-190 see also: Correction to Algorithm AS 183 Applied Statistics 33 (1984) 123 McLeod, A. I. (1985) A remark on Algorithm AS 183 Applied Statistics 34 (1985),198-200 USE: whrandom.random() yields double precision random numbers uniformly distributed between 0 and 1. whrandom.seed(x, y, z) must be called before whrandom.random() to seed the generator There is also an interface to create multiple independent random generators, and to choose from other ranges. Multi-threading note: the random number generator used here is not thread-safe; it is possible that nearly simultaneous calls in different theads return the same random value. To avoid this, you have to use a lock around all calls. (I didn't want to slow this down in the serial case by using a lock here.) """ import warnings warnings.warn("the whrandom module is deprecated; please use the random module", DeprecationWarning) # Translated by Guido van Rossum from C source provided by # Adrian Baddeley. class whrandom: def __init__(self, x = 0, y = 0, z = 0): """Initialize an instance. Without arguments, initialize from current time. With arguments (x, y, z), initialize from them.""" self.seed(x, y, z) def seed(self, x = 0, y = 0, z = 0): """Set the seed from (x, y, z). These must be integers in the range [0, 256).""" if not type(x) == type(y) == type(z) == type(0): raise TypeError, 'seeds must be integers' if not (0 <= x < 256 and 0 <= y < 256 and 0 <= z < 256): raise ValueError, 'seeds must be in range(0, 256)' if 0 == x == y == z: # Initialize from current time import time t = long(time.time() * 256) t = int((t&0xffffff) ^ (t>>24)) t, x = divmod(t, 256) t, y = divmod(t, 256) t, z = divmod(t, 256) # Zero is a poor seed, so substitute 1 self._seed = (x or 1, y or 1, z or 1) def random(self): """Get the next random number in the range [0.0, 1.0).""" # This part is thread-unsafe: # BEGIN CRITICAL SECTION x, y, z = self._seed # x = (171 * x) % 30269 y = (172 * y) % 30307 z = (170 * z) % 30323 # self._seed = x, y, z # END CRITICAL SECTION # return (x/30269.0 + y/30307.0 + z/30323.0) % 1.0 def uniform(self, a, b): """Get a random number in the range [a, b).""" return a + (b-a) * self.random() def randint(self, a, b): """Get a random integer in the range [a, b] including both end points. (Deprecated; use randrange below.)""" return self.randrange(a, b+1) def choice(self, seq): """Choose a random element from a non-empty sequence.""" return seq[int(self.random() * len(seq))] def randrange(self, start, stop=None, step=1, int=int, default=None): """Choose a random item from range(start, stop[, step]). This fixes the problem with randint() which includes the endpoint; in Python this is usually not what you want. Do not supply the 'int' and 'default' arguments.""" # This code is a bit messy to make it fast for the # common case while still doing adequate error checking istart = int(start) if istart != start: raise ValueError, "non-integer arg 1 for randrange()" if stop is default: if istart > 0: return int(self.random() * istart) raise ValueError, "empty range for randrange()" istop = int(stop) if istop != stop: raise ValueError, "non-integer stop for randrange()" if step == 1: if istart < istop: return istart + int(self.random() * (istop - istart)) raise ValueError, "empty range for randrange()" istep = int(step) if istep != step: raise ValueError, "non-integer step for randrange()" if istep > 0: n = (istop - istart + istep - 1) / istep elif istep < 0: n = (istop - istart + istep + 1) / istep else: raise ValueError, "zero step for randrange()" if n <= 0: raise ValueError, "empty range for randrange()" return istart + istep*int(self.random() * n) # Initialize from the current time _inst = whrandom() seed = _inst.seed random = _inst.random uniform = _inst.uniform randint = _inst.randint choice = _inst.choice randrange = _inst.randrange ```
Tip: Filter by directory path e.g. /media app.js to search for public/media/app.js.
Tip: Use camelCasing e.g. ProjME to search for ProjectModifiedEvent.java.
Tip: Filter by extension type e.g. /repo .js to search for all .js files in the /repo directory.
Tip: Separate your search with spaces e.g. /ssh pom.xml to search for src/ssh/pom.xml.
Tip: Use ↑ and ↓ arrow keys to navigate and return to view the file.
Tip: You can also navigate files with Ctrl+j (next) and Ctrl+k (previous) and view the file with Ctrl+o.
Tip: You can also navigate files with Alt+j (next) and Alt+k (previous) and view the file with Alt+o.