Index: Lib/random.py =================================================================== --- Lib/random.py (revision 82067) +++ Lib/random.py (working copy) @@ -168,9 +168,7 @@ raise ValueError("non-integer arg 1 for randrange()") if stop is default: if istart > 0: - if istart >= maxwidth: - return self._randbelow(istart) - return int(self.random() * istart) + return self._randbelow(istart) raise ValueError("empty range for randrange()") # stop argument supplied. @@ -192,9 +190,7 @@ # a long, but we're supposed to return an int (for backward # compatibility). - if width >= maxwidth: - return int(istart + self._randbelow(width)) - return int(istart + int(self.random()*width)) + return istart + self._randbelow(width) if step == 1: raise ValueError("empty range for randrange() (%d,%d, %d)" % (istart, istop, width)) @@ -212,9 +208,7 @@ if n <= 0: raise ValueError("empty range for randrange()") - if n >= maxwidth: - return istart + istep*self._randbelow(n) - return istart + istep*int(self.random() * n) + return istart + istep*self._randbelow(n) def randint(self, a, b): """Return random integer in range [a, b], including both end points. @@ -222,7 +216,7 @@ return self.randrange(a, b+1) - def _randbelow(self, n, _log=_log, int=int, _maxwidth=1<= rmax: + r = int(self.random() * _maxwidth) + # Could use r % n here instead. That would be fine for MT, but + # would behave poorly for PRNGs with low entropy in the low-order + # bits of random(). r // quot is safer in general. + return r // quot + try: getrandbits = self.getrandbits except AttributeError: @@ -239,14 +247,13 @@ # has not been overridden or if a new getrandbits() was supplied. # This assures that the two methods correspond. if type(self.random) is _BuiltinMethod or type(getrandbits) is _Method: - k = int(1.00001 + _log(n-1, 2.0)) # 2**k > n-1 > 2**(k-2) + k = (n-1).bit_length() # 2**k > n-1 >= 2**(k-1) r = getrandbits(k) while r >= n: r = getrandbits(k) return r - if n >= _maxwidth: - _warn("Underlying random() generator does not supply \n" - "enough bits to choose from a population range this large") + _warn("Underlying random() generator does not supply \n" + "enough bits to choose from a population range this large") return int(self.random() * n) ## -------------------- sequence methods -------------------