How would I quickly and safely* determine a random number within a range of 0 (inclusive) to r (exclusive)?
In other words, an optimized version of rejection sampling:
u32 myrand(u32 x)
{
u32 ret = rand();
while(ret >= x)
ret = rand();
return(ret);
}
*By safely, I mean a uniform distribution.
Rejection sampling is the way to go if you want to have a uniform distribution on the result. It is notoriously difficult to do anything smarter. Using the modulo operator for instance results in an uneven distribution of the result values for any number that’s not a power of 2.
The algorithm in you post however can be improved by discarding the unnecessary most significant bits. (See below.)
This is how the standard Java API implements
Random.nextInt(int n):And in the commens you can read: