Using SHA1 as RNG

Klaus Alexander Seistrup spam at magnetic-ink.dk
Fri Mar 14 13:14:12 EST 2003


I was looking at python's whrandom and random modules the other day.
Both seem to have a period of 27814431486575L (30268*30306*30322-1),
which is, of course, quite a number, but not that long anyway.  So I
thought, why not use SHA1 in the core generator?  Perhaps something
along these lines:

#v+

import sys, os, time, sha

class SHARandom:
    def __init__(self, x = 0, y = 0,  z = 0):
        self._max = float(long('f'*40,16)+1)
        self._sha = sha.new()
        self.seed(x, y, z)
    # end def __init__

    def seed(self, x = 0, y = 0, z = 0):
        if not x: x = `time.time()`
        if not y: y = os.getpid()
        if not z: z = os.getcwd()
        self._sha.update(str(x))
        self._sha.update(str(y))
        self._sha.update(str(z))
    # end def seed

    def random(self):
        self._hash = self._sha.digest()
        self._sha.update(self._hash)
        return float(long(self._sha.hexdigest(), 16)) / self._max
    # end def random

    # [ methods omitted for brevity ]

# end class SHARandom

# Initialize from the current time
_inst = SHARandom()
seed = _inst.seed
random = _inst.random
uniform = _inst.uniform
randint = _inst.randint
choice = _inst.choice
randrange = _inst.randrange

#v-

It is probably quite expensive to use the sha module for shuffling
the bits, but the resulting period is huge.

What do you guys think?  Is it worth it?  I meant to use it for
generating uuids, but perhaps it's overkill?


  // Klaus

-- 
 ><> 	unselfish actions pay back better




More information about the Python-list mailing list