Flexible Random Number Generation

Started by
14 comments, last by stay in school 19 years, 7 months ago
Check out the "Numerical Recipes in C" book, chapter 7.
"Debugging is twice as hard as writing the code in the first place. Therefore, if you write the code as cleverly as possible, you are, by definition, not smart enough to debug it." — Brian W. Kernighan
Advertisement
i'm using
// return value is in range 0..n-1 // No divide needed(% is as costly as divide)inline int random(int n,uint32 &rseed)//minor fix for case we're on 64 bit system{    rseed *= 0x08088405;    rseed += 1 ;    return ((uint64)((uint32)rseed))*((uint64)((uint32)n))>>32 ;}

it's standard generator used in Borland Delphi.I heard it's not very very good(anyway,most programs will not notice) but it's VERY fast(assuming your compiler will optimize thing that "looks like 64 bit multiply" to single "mul" opcode (on x86, normal 32 bit multiply gives 64 bit result.) MSVC .net optimizes it well. )

uint32 and uint64 is a unsigned 32 and 64 bit integers.

[Edited by - Dmytry on August 28, 2004 1:13:10 AM]
I still maintain that my random number generator will generate the most random numbers. The BBS system, while slow, is better than any form of LFSR/GFSR, even when you take 4 bits from each number, rather than 1, and when you take 4 bits from each number it only takes about 1 second to generate a number.
Quote:Original post by jperalta
I still maintain that my random number generator will generate the most random numbers. The BBS system, while slow, is better than any form of LFSR/GFSR, even when you take 4 bits from each number, rather than 1, and when you take 4 bits from each number it only takes about 1 second to generate a number.
Of course, simple Linear Congruence generators are good enough for just about everything, and the Mersenne Twister has you beat (both in 'randomness' and most probably speed as well, but its state is rather large).

Edit: I'm going to have to disagree with you about the BBS system entirely. I don't know PRNG theory well, but it looks like a rather poor algorithm. You're reducing the period by a factor of 32 since you're generating one number per bit using a single seed, plus it goes to a lot of trouble to initialize the seed to itself (unless it is a multiple of P or Q, which could be tested with two conditional statements).
There are a few other 'intereting' details but I'm too tired to really examine the code and like I said I really don't know PRNG theory so I could be completely wrong.
"Walk not the trodden path, for it has borne it's burden." -John, Flying Monk
My implementation is pretty poor, but I'm not 100% sure you actually have to test to generate the relative prime because as I recall if you have primes p and q and n = p*q then any number m != p & != q should be relatively prime to n.

Edit: Yeah, that's right, I should actually take the call to FindRelativePrime() and just fail if the user gives p or q as the seed or if the GCD between n and seed != 1, but that can only occur if seed > n and n|seed which is a very unlikely situation.

[Edited by - jperalta on August 27, 2004 7:24:24 PM]
Quote:Original post by ShmeeBegek
I am using MSVC++ 6, and it doesn't seem to have any libraries included for re-entrant (and more flexible) random number generation.
Take a look at the CryptGenRandom() function. It generates cryptographically strong pseudo-random numbers in the form of a byte array.
#include <windows.h>#include <wincrypt.h>...static HCRYPTPROV hProv;result = CryptAcquireContext(&hProv, 0, 0, PROV_RSA_FULL, CRYPT_VERIFYCONTEXT);...unsigned int randomNumber;result = CryptGenRandom(hProv, sizeof(int), (unsigned char*)&randomNumber);...result = CryptReleaseContext(hProv, 0);

This topic is closed to new replies.

Advertisement