One common way of choosing a random number in [0, n) is to take the result of rand()
modulo n: rand() % n
. However, even if the results returned by the available rand()
implementation are fully uniform, shouldn't there be a problem with the uniformity of the resulting [0, n) numbers when RAND_MAX + 1
does not divide evenly by n? E.g. suppose RAND_MAX
is 2, and n is 2. Then out of 3 possible rand()
outputs: 0, 1 and 2, we get 0, 1 and 0 respectively when we use them modulo n. Therefore the output will not be uniform at all.
Is this a real problem in practice? What is a better way of choosing random numbers in [0, n) uniformly deriving from rand()
output, preferably without any floating point arithmetic?
Then out of 3 possible rand() outputs: 0, 1 and 2, we get 0, 1 and 0 respectively when we use them modulo n. Therefore the output will not be uniform at all.
The Uniform Random Number block generates uniformly distributed random numbers over a specifiable interval with a specifiable starting seed. The seed is reset each time a simulation starts. The generated sequence is repeatable and can be produced by any Uniform Random Number block with the same seed and parameters.
Use rand to generate 1000 random numbers from the uniform distribution on the interval (0,1). rng('default') % For reproducibility u = rand(1000,1); The inversion method relies on the principle that continuous cumulative distribution functions (cdfs) range uniformly over the open interval (0,1).
Use the modulo (%) operator to generate random numbers within a specific range. The example below generates whole numbers within a range of 1 to 6. int main () { for (int x = 1; x <= 10; x++) { cout << 1 + (rand() % 6) << endl; } } /* Output: 6 6 5 5 6 5 1 1 5 3 */ but when i wish to use range between 2 to 9 .
You are correct, rand() % N
is not precisely uniformly distributed. Precisely how much that matters depends on the range of numbers you want and the degree of randomness you want, but if you want enough randomness that you'd even care about it you don't want to use rand()
anyway. Get a real random number generator.
That said, to get a real random distribution, mod to the next power of 2 and sample until you get one in the range you want (e.g. for 0-9, use while(n = rand()%0x10 > 10);
).
That depends on:
Let us assume your RAND_MAX is 2^32. If N is rather small (let's say 2) then the bias is 1 / 2^31 -- or too small to notice.
But if N is quite a bit larger, say 2^20, then the bias is 1 / 2^12, or about 1 in 4096. A lot bigger, but still pretty small.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With