Random number not so random afterall

Hey Guys.

I am new at coding, and I wanted to make a little game using the random number generator. Below you see the way I learned to make a random number generator. The problem is, that this is not as random as you would have thought. The number keeps increasing with the same amount everytime I run the compiler (however it depends on how long I wait when I run it again). I can basically guess what the "random" number is a lot of the time. I know it uses time, but it adds like 10 to the random number for every second. So why can't it be more random? And is there a way to make it more random?
And is there another way to make random numbers than this too?

Thanks! :D

1
2
3
4
5
6
7
8
9
10
11
#include <iostream>
#include <cstdlib>
#include <ctime>
using namespace std;

int main()
{
srand (time(0));
cout << rand()%100+1 << endl;

}
Given the weight of a die, it's orientation and it's initial velocity the out come of any dice roll can be calculated before it even lands. If you record the order in which the cards in a deck are stacked and then serialize all of the interactions with that deck then you will know the order in which they will appear. My point is OP, nothing is truly random; so how close does this solution need to be?
Some implementation of rand() returns current state before advancing it. That means that first returned value will be seed it was initialized with. Do warm-up of your RNG by doing something like:
1
2
for(int i = 0; i < 10; ++i)
    rand();
and try again
It still shouldn't be as predictable as the OP claims it is.

What compiler and version are you using, and what OS?


You might want to use the Mersenne Twister algorithm in the current standard library:
http://www.cplusplus.com/reference/random/mersenne_twister_engine/mersenne_twister_engine/
I am using Code:Blocks version 13:12.

It is really predictable. I tried to run it 4 times and the outcome was
2. 5. 12. 15. 19 etc. (increasing by a small amount every second) I ran it about once every second. Shouldn't it be more like 55. 23. 67. 34 etc.? Shouldn't the algorithm for the rand() function not be more complex than increasing the value by 5 each second or so? (Try to run it yourselves, do you get the same result?)

However I tired to do this:
1
2
3
      srand (time(0));
      rand();
      cout << rand()%100+1 << endl

and it actually worked a whole lot better!.

And I don't really understand the Mersenne Twister Algorithm, I am not there yet, so far I am learning about inheritance :)
If you go to the installation directory for MingW and enter mingw32-C++.exe --version what GCC version does it say you are using? The release notes for GCC 4.8 mention the addition of hardware support to the RNG. I'm reaching here of course, this is a really weird issue and I'm not sure where to start.
I found the directory, but I couldn't find the .exe file. But I think the version is. 4.7.1 as you can see on this screenshot I took: http://imgur.com/lJrWI9C

Have you tried the code and seen if it works with your compiler? :)

and thanks for helping out!
Using MinGW GCC 4.8.1 32-bit, the effect can be simulated like this:
1
2
3
4
5
6
7
8
9
10
    unsigned seed = 1402678758;
    
    for (int i=0; i<10; i++)
    {
        srand (seed++);
        rand();
        cout << rand() << endl;
    }
7593
18342
29090
7070
17819
28567
6548
17296
28044
6025

When line 6 is commented out, this is the result:
18232
18235
18238
18241
18245
18248
18251
18255
18258
18261
Last edited on
It does, you have to go to the installation directory from the command shell though. The binary mingw32-C++.exe is in "%INSTALLED_DIRECTORY%\Mingw\bin".

Regardless I think you are correct, you are running an older version of the compiler. You should update MingW-Get from here: http://sourceforge.net/projects/mingw/files/latest/download?source=files
Ok, so I just updated it with the link you gave me. Using the command shell is really confusing because i've never used it before. However I got the same output as Chervil ^^, when I used his code.. Really weird.
What IDE/Compiler do you use? Because in my computer the mingw32-c++.exe is under "C:\Program Files (x86)\CodeBlocks\MinGW\bin".
His code was written so that it re-seeded rand() on purpose, that's not what you are doing is it?
Yes, I forgot to add that under normal circumstances it is not necessary to call srand() more than once. The only reason I did so was to simulate the effect of re-running a program repeatedly within a short timescale.
I just use the random_device object in the std library, rand() is old c language.

Example:
1
2
3
4
5
6
7
8
9
10
11
12
13
#include "stdafx.h"
#include "iostream"
#include "stdlib.h"
#include "random"

using std::cout; using std::cin; using std::endl;using std::random_device;
/*Main method*/
void _tmain(int argc, _TCHAR* argv[])
{
	random_device randNum;
	int rand = randNum() % 100;
        cout << rand << endl;
}
From http://www.cplusplus.com/reference/random/random_device/

True random number generator
A random number generator that produces non-deterministic random numbers, if supported.

Unlike the other standard generators, this is not meant to be an engine that generates pseudo-random numbers, but a generator based on stochastic processes to generate a sequence of uniformly distributed random numbers. Although, certain library implementations may lack the ability to produce such numbers and employ a random number engine to generate pseudo-random values instead. In this case, entropy returns zero.

Notice that random devices may not always be available to produce random numbers (and in some systems, they may even never be available). This is signaled by throwing an exception derived from the standard exception on construction or when a number is requested with operator().

Unless the program really requires a stochastic process to generate random numbers, a portable program is encouraged to use an alternate pseudo-random number generator engine instead, or at least provide a recovery method for such exceptions.


And from http://en.cppreference.com/w/cpp/numeric/random/random_device

// note: demo only: the performance of many
// implementations of random_device degrades sharply
// once the entropy pool is exhausted. For practical use
// random_device is generally only used to seed
// a PRNG such as mt19937


Just because it is newer does not mean it is better. The impression I got from a quick look at random_device is that it is best used to seed a pseudo random number generator as commented in that last link. That is the also the way I see it used in may examples at SO. In other words it is a replacement for srand(), not rand().
In other words it is a replacement for srand(),
More like replacement to time(nullptr) :)
Can't expect 5 minutes of research to be perfect :)
Topic archived. No new replies allowed.