1. ## Random Number Issues

So. What I am attempting to do is to get the program to spit out a random number somewhere between 1 and 10,000. It's not working quite the way I want, specifically, the numbers end up being low, for some reason.

Basically, I just ran a loop 10,000 times, where the program kept spitting out random numbers (1-10000) and every time made a note of whether or not the random number was above or below the middle number (5000 in this case.) The program consistently spits out numbers from 1-10000 that are only 5001 or above maybe 4500 times out of 10000. Which is just plain out bizarre. I ran the same program for numbers 1-6 and it came right down the middle, around 5000 of the 10000 numbers were 4+.

What am I doing wrong? (It is possible that this is actually a malfunction of the testing function, and not the generator itself, but that in and of itself would be interesting to know.)

Thanks for your patience, trying to learn C++ quickly to test some things out that can't be done in a spreadsheet.

2. If you post the code, we can possibly comment on whether you are doing something wrong in your code. And of course, different C compilers have different (quality of) random number generators, so if you tell us which compiler/OS you are using, someone may be able to tell whether this is what can be expected.

--
Mats

3. O_o

Why should it be even? If a random number generator spits out 4 for ten thousands rounds that wouldn't make it less random.*

That asked, why don't you post what you have?!

Soma

*(I only bring this up because PRNG basically sample a few bits at a time from some huge number. Depending on the algorithm, you are guaranteed to occasion upon an "area" of the expansion that returns the same number for "a very long time".)

4. int x, z;
time_t seconds;
time(&seconds);
z=0;
srand((unsigned int) seconds);
for (int y=0;y<10000;y++)
{
x=rand() % (5000) +1 ;
if (x>=2500) {z++;}
}

5. If you're using the % modulus operator to range your random numbers from rand, then this would be the issue. Why?

Suppose that the distribution from rand() is completely uniform from 0 to RAND_MAX. With some systems, I believe RAND_MAX is about 32767. Since the top is at 32767, and not some number evenly divisible by 10000, numbers from 0 - 2767 are more likely to occur. It's about 1.33 times more likely to get a number 2767 or below than any number above.

Edit: I see that you are using the modulus operator.

A better conversion:

int r = (rand() * 5000) / (RAND_MAX + 1);

The only issue is that you might need to be careful of overflow if the implementation yields large numbers from rand().

6. Honestly, what I want is to figure out how to get my consistently random 1-10000 numbers. Troubleshooting what I have is good, but if someone knows how to do it in a different way, I'm all about that. I've read a lot of mixed information on the best way to do random numbers, so I'm mostly winging it. I'm running the Code::Block 8.02 compiler, for what it is worth.

Again, thanks for bearing with me

7. Originally Posted by sansterre
Thanks for your patience, trying to learn C++ quickly to test some things out that can't be done in a spreadsheet.
You mean, you haven't yet figured out that you could fill 4000 rows of a spreadsheet with random numbers (ok, so the formula to make a 1..10000 number would be something like this: =int(10000 * rand() + 1), and then you do =countif(A1:A4000, ">5000").

As Soma says, the distribution of random numbers in C/C++ is not guaranteed to be equal on both sides of the middle. If you want that for a serious reason, then perhaps you should be looking for a "real" pseudo-random number generator. Mersenne-Twister is a few dozen lines of code - available on the Web by the original authors that came up with the algorithm.

For simple games and simulatiokns (and rather complex ones, for that matter), rand() is usually fine. For something that is commercially important (e.g. games of chance for real money on a website) you want something that is slightly less predictable.

--
Mats

8. Here's a quick comparison of the different ways of scaling the output of rand()

Code:
```#include <stdio.h>
#include <stdlib.h>

int main()
{
int y = 0;
for(; y < 5; y++) {
printf("Trial %d\n", y);
int r1 = 0, r2 = 0;

int x = 0;
for(; x < 10000; x++) {
if(rand() % 10000 >= 5000) r1++;
}

for(x = 0; x < 10000; x++) {
if((rand() * 10000) / (RAND_MAX + 1) >= 5000) r2++;
}

printf("Results for rand() %% 10000: %d\n", r1);
printf("Results for (rand() * 10000) / (RAND_MAX + 1): %d\n\n", r2);
}

return 0;
}```
And the results:
Trial 0
Results for rand() % 10000: 4557
Results for (rand() * 10000) / (RAND_MAX + 1): 5090

Trial 1
Results for rand() % 10000: 4575
Results for (rand() * 10000) / (RAND_MAX + 1): 5036

Trial 2
Results for rand() % 10000: 4563
Results for (rand() * 10000) / (RAND_MAX + 1): 5041

Trial 3
Results for rand() % 10000: 4546
Results for (rand() * 10000) / (RAND_MAX + 1): 4976

Trial 4
Results for rand() % 10000: 4552
Results for (rand() * 10000) / (RAND_MAX + 1): 5028

It's clear that the scaling method is significant.

9. Tjb, thank you. Your suggested alterations seem to work perfectly.

Much appreciated,

Sansterre