views:

1277

answers:

7

I need to generate a unique ID based on a random value.

+3  A: 

Here ya go:

import os
id = os.urandom(32)
chaos
+6  A: 

Perhaps uuid.uuid4()? See: uuid.

Michael Aaron Safyan
Watch out, the library underlying that module is buggy and tends to fork a process that keeps FDs open. That's fixed in newer versions, but most people probably don't have that yet, so I generally avoid this module. Caused me major headaches with listen sockets...
Glenn Maynard
+4  A: 

You might want Python's UUID functions:

21.15. uuid — UUID objects according to RFC 4122

DreadPirateShawn
A: 

Maybe the uuid module?

zenazn
A: 
import time
def new_id():
    time.sleep(0.000001)
    return time.time()

On my system, time.time() seems to offer 6 significant figures after the decimal point. With a brief sleep it should be guaranteed unique with at least a moderate amount of randomness down in the last two or three digits.

You could hash it as well if you're worried.

John Fouhy
Hashing it won't make it any more unique, and there's a strong chance of a collision eventually if more than one process is doing this--anywhere, not even just on the same machine. This is no way to generate unque IDs.
Glenn Maynard
Hashing will stop people guessing by incrementing. It'll be unique if there's only one thread handing out IDs, I think. A lot depends on what the IDs are _for_. (and why they have to be both unique and random)
John Fouhy
A: 

unique and random are mutually exclusive. perhaps you want this?

import random
def uniqueid():
    seed = random.getrandbits(32)
    while True:
       yield seed
       seed += 1

Usage:

unique_sequence = uniqueid()
id1 = unique_sequence()
id2 = unique_sequence()
id3 = unique_sequence()
ids = [unique_sequence() for dummy in range(1000)]

no two returned id is the same (Unique) and this is based on a randomized seed value

TokenMacGuy
This isn't unique. If I start it twice, and generate a million values each time, the chances of a collision between the two runs is significant. I'd have to store the last "seed" each time to avoid that--and then there's no point to having the seed; it's just a sequence generator. *Statistically* unique IDs typically are generated from random data; at least one class of UUIDs works that way.
Glenn Maynard
It is unique so long as each unique sequence comes from only a single invocation of uniqueid. there is no guarantee of uniqueness across generators.
TokenMacGuy
With that condition, even a counter is unique.
Glenn Maynard
is there something wrong with generating unique ID's by means of a counter? this is a common practice in databse design.
TokenMacGuy
A: 
def guid( *args ):
    """
    Generates a universally unique ID.
    Any arguments only create more randomness.
    """
    t = long( time.time() * 1000 )
    r = long( random.random()*100000000000000000L )
    try:
        a = socket.gethostbyname( socket.gethostname() )
    except:
        # if we can't get a network address, just imagine one
        a = random.random()*100000000000000000L
    data = str(t)+' '+str(r)+' '+str(a)+' '+str(args)
    data = hashlib.md5(data).hexdigest()

    return data
mluebke