views:

841

answers:

11

How can a random number be generated from scratch, i.e without using any built-in features of the language / outside API that will help with the randomization process?

For example php has a rand() function and a seed function, and I'm sure java also has some similar stuff.

You can use built-in functions to get the current time etc, but the actual process of generating a random number has to be done by your code.

Any ideas?

A: 

Use system clock. Then hash it.

Tom R
Hm, the question says "without using any built-in features of the language / outside API that will help with the randomization process", so using a hash function might not be allowed...
sleske
I know that this post was [probably] meant as a "mental exercise", but in case someone reads your post and thinks "Hey, nice idea, I'll use that in my program!"....Please don't do that. You want your seed/entropy to be non-obvious, otherwise it's too easy to figure out what's coming next. That's a bad thing when dealing with session ids, encryption keys, etc.
Sam Bisbee
+2  A: 

Take some initial seed number and multiply it with a large and well picked number to produce new pseudo-random numbers. Actually, this is what many languages do.

int seed = 94664704;
public int rand() {
    seed = 23*seed % 10e8 + 1;
    return seed % 10e5;
}

Taken from my highschool formula collection, Formeln und Tafeln, page 8.

Adrian
Well, just what makes a number "well picked"?
sleske
I guess Knuth discusses that to full length...
Adrian
+11  A: 

Java actually details how they pick the next random number in the javadoc for java.util.Random:

The general contract of next is that it returns an int value and if the argument bits is between 1 and 32 (inclusive), then that many low-order bits of the returned value will be (approximately) independently chosen bit values, each of which is (approximately) equally likely to be 0 or 1. The method next is implemented by class Random as follows:

 synchronized protected int next(int bits) {
    seed = (seed * 0x5DEECE66DL + 0xBL) & ((1L << 48) - 1);
    return (int)(seed >>> (48 - bits));
 }

This is a linear congruential pseudorandom number generator, as defined by D. H. Lehmer and described by Donald E. Knuth in The Art of Computer Programming, Volume 2: Seminumerical Algorithms, section 3.2.1.

Matt
Beware that this is pseudo-random not random, and that if you supply the same seed you will get the same sequence of numbers.
Stephen C
@Stephen: Isn't that the case with _every_ computer based number generator? I mean, there is no thing like _real_ random number generation, as long as you take something into what is random (like atmospheric noise or something).
Bobby
No, most depend on entropy in the system, and not solely or at all on some seed.
Alex
+10  A: 
ilya n.
hehe. Were ever truer things drawn?
Tom R
+3  A: 

Implement a linear congruential generator -- simple, and reasonably high quality for well chosen parameters.

Alex Martelli
+1  A: 

Wikipedia's discussion of the linear congruential generator is decent and accessible, if you're hell-bent on doing this yourself:

http://en.wikipedia.org/wiki/Random%5Fnumber%5Fgeneration#Computational%5Fmethods

Though I can't imagine why you'd want to do this yourself; most decent languages and/or operating environments already provide tested sources of pseudo-randomness.

Brian Clapper
+2  A: 

If you need a good quality random number, then you should look in to implementing the Mersenne twister random number generator in your language of choice. There are a lot of ready implementations floating around the net, so you can just pick one that you'd like to use.

If you can deal with something cruddy, just use a linear congruential generator.

Nakedible
A: 

Your question is a bit unclear. Are you trying to solve a concrete problem? Are you just asking out of curiosity?

If I understand you correctly, you want to re-implement the random-number generation that most languages/APIs offer. To do this, you'll have to implement a pseudo-random generator. This is a rather complex mathematical topic (if you want to do it correctly), so be prepared to do a lot of reading and thinking. A good starting point would be the Wikipedia article on Pseudorandom number generators

sleske
A: 

most languages have a PRNG function like Math.random() in java. The PRNG is usually seeded with a value like the current time or something you choose.

For something more secure, you need a greater source of entropy than the current time. A class like java.security.SecureRandom implements that.

One high quality PRNG is the Mersenne Twister algorithm.

There are much simpler PRNG's for more basic applications, like this one from the C documentation:

int rand(void)
{
  next = next * 1103515245 + 12345;
  return (unsigned int)(next/(2 * (RAND_MAX +1L)) % (RAND_MAX+1L));
}

void srand(unsigned int seed)
{
  next = seed;
}

You can test the quality of your PRNG using this tester: http://www.phy.duke.edu/~rgb/General/dieharder.php

jspcal
A: 

Computers being discrete mathematical device are incapable of generating pure random number without external intervention. Below code generates fairly usable random number:

public static synchronized String getAutoGenId(){
    StringBuilder autogenID=new StringBuilder();
    try 
    {   

        Random rand = new Random();
        autogenID.append(Long.toString(System.nanoTime()));
        autogenID.append(Integer.toString(rand.nextInt(99)));
        if(autogenID.toString().length()<15)
        {
            autogenID.append(Integer.toString(rand.nextInt(9)));
        }

    } catch (Exception e) {
        //Do something
    } 
    return autogenID.toString();
}

Or else you may also find it interesting to study the implementation of UUID

Ravi Gupta
Not clear what half this method does. perhaps you could add some comments like why you wait 10 milli-seconds and why you create a Date object only to extract the current time millis. Why create random numbers of between 0-98 or 0-8 instead of 0-99 or 0-9. Why use StringBuffer instead of StringBuilder.
Peter Lawrey
You could consider using System.nanoTime() which is what new Random() does and just generate a simple number or two without using Strings.
Peter Lawrey
-1: Seems very strange. And unless the poster can describe and explain why it is implemented as it is I call bogus.
kigurai
Thanks for the input, made some changes as per comments, this is not an example of best (pseudo)random generator, this is just what we use to get 15 char length key for our use.
Ravi Gupta
A: 

If you want truly random, you must build a dice rolling robot and then program it accordingly. Or buy the one this dude made:

DiceOMatic

Andrew Heath