BUT the first pseudo-random number is quite always the same from one run to another. It slowly evolve from n to n+1 from time to time ...
The following numbers obtained with rand() are just fine.
Replacing 'RAND_MAX' by a small constant like 1, I see where the problem come from: say at #1 run I get 743800, I'll get 744000 at #2 run
I get no such problem under Linux (except output of printf, just replacing RAND_MAX by RAND_MAX/1000 and not 1 is OK).
I know older versions of Windows had serious problems with pseudo-random numbers and that they could even be guessed after a few tries with net hacks, but thought that it was fixed with Win2k and later.
Is this where the problem comes from? Or from a lib that isn't the same in Dev-C++/gcc and Linux/gcc? Or a problem with 'higher/lower bits' used by srand/rand (don't think so)?
Or am I far from the solution? :-D
Is there a better function under Windows or should I consider writing a small 'rand2' function that should diverge with quite similar seeds?
Using: WinXP Home and Dev-C++ 4.9.8.0
Log: just fine (and in French)
Compilateur: Default compiler
Excution de gcc.exe...
gcc.exe "C:\Documents and Settings\Jacques\Bureau\random3.c" -o "C:\Documents and Settings\Jacques\Bureau\random3.exe" -g3 -I"C:\Dev-Cpp\include" -L"C:\Dev-Cpp\lib"
Excution termine
Compilation OK
Thanks in advance,
Jacques
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
Your approach to generating random numbers in the range [0,99] makes use of the higher bits of the value returned by rand(). A more common approach is to use rand()%100, which uses the lower bits of the value instead. Why is this relevant? Because the call to srand(time(0)) seeds the current time, and so the high bits will remain similar for two consecutive runs, giving you the results you are getting.
To see this more clearly, print the floating point value in full. Try this main function and run the program a few times, it will make the difference clear:
int main() {
int first;
srand(time(0));
first = rand();
printf("First: %d -- %f -- %d\n", first, 100.0 * first / (1.0 + RAND_MAX), first % 100);
system("PAUSE");
return(0);
}
qWake
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
I noticed something having nothing whatsoever to do with random number properties, but not unimportant. Looking where your file you are compiling is:
C:\Documents and Settings\Jacques\Bureau\random3.c
I see you have put it in a directory with spaces in the path. You can get away with this for compiuling a single file, but eventually, it will bite you when you compile a project. Avoid spaces. *Please*
:-)
Wayne
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
There are many relatively simple ways to "fake up" some "noise" for input into a randomizing scheme. One of the "cheapest" is user input, if the program can work that way.
There's a great deal of literature on the topic. Try a Google search on some key terms....
-- Jim.
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
the random number generation doesn't come from Windows but from the msvcrt library (which mingw uses, in all win32 versions); for me, the greatest defect it has is the small RAND_MAX
but you are also right: when you seed the generator, the first rand is too dependent on the seed
one solution is to call rand once or twice after srand, without using the values:
srand((unsigned) time(NULL)); //or shortly: srand(time(0));
rand();
rand();
and then you can do what you want
there are some random generators whose lower bits are "less random" (and in that case, you have to use the higher bits), but I think the one in msvcrt is not of that kind
if you want to know more about generating random numbers, read Knuth (The Art of Programming) vol. 2
Adrian
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
For some purposes, I use the Gnu Scientific Library (GSL) of random numbers. It has a large number of random distributions available. If you search the forum, you should find a couple of places where I talk about how to find it and set it up.
Wayne
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
Hi,
Trying to get rid of Borland randomize()/random(), I (with help from Google and this forum) managed to write this:
--------------------------------
#include <stdlib.h>
#include <stdio.h>
#include <time.h>
#define DIVIDE RAND_MAX
int i;
int main(void)
{
srand((unsigned) time(NULL));
printf("The first \"pseudo-random\" number is: ");
printf("%d\n", (int) (100.0*rand()/(DIVIDE+1.0)) );
printf("Next numbers are:");
for (i=1; i<=7; i++)
printf(" %d ", (int) (100.0*rand()/(DIVIDE+1.0)) );
printf("\n\n\n\n");
system("PAUSE");
return(0);
}
----------------------------------
BUT the first pseudo-random number is quite always the same from one run to another. It slowly evolve from n to n+1 from time to time ...
The following numbers obtained with rand() are just fine.
Replacing 'RAND_MAX' by a small constant like 1, I see where the problem come from: say at #1 run I get 743800, I'll get 744000 at #2 run
I get no such problem under Linux (except output of printf, just replacing RAND_MAX by RAND_MAX/1000 and not 1 is OK).
I know older versions of Windows had serious problems with pseudo-random numbers and that they could even be guessed after a few tries with net hacks, but thought that it was fixed with Win2k and later.
Is this where the problem comes from? Or from a lib that isn't the same in Dev-C++/gcc and Linux/gcc? Or a problem with 'higher/lower bits' used by srand/rand (don't think so)?
Or am I far from the solution? :-D
Is there a better function under Windows or should I consider writing a small 'rand2' function that should diverge with quite similar seeds?
Using: WinXP Home and Dev-C++ 4.9.8.0
Log: just fine (and in French)
Compilateur: Default compiler
Excution de gcc.exe...
gcc.exe "C:\Documents and Settings\Jacques\Bureau\random3.c" -o "C:\Documents and Settings\Jacques\Bureau\random3.exe" -g3 -I"C:\Dev-Cpp\include" -L"C:\Dev-Cpp\lib"
Excution termine
Compilation OK
Thanks in advance,
Jacques
Your approach to generating random numbers in the range [0,99] makes use of the higher bits of the value returned by rand(). A more common approach is to use rand()%100, which uses the lower bits of the value instead. Why is this relevant? Because the call to srand(time(0)) seeds the current time, and so the high bits will remain similar for two consecutive runs, giving you the results you are getting.
To see this more clearly, print the floating point value in full. Try this main function and run the program a few times, it will make the difference clear:
int main() {
int first;
srand(time(0));
first = rand();
printf("First: %d -- %f -- %d\n", first, 100.0 * first / (1.0 + RAND_MAX), first % 100);
system("PAUSE");
return(0);
}
qWake
Jacques,
I noticed something having nothing whatsoever to do with random number properties, but not unimportant. Looking where your file you are compiling is:
C:\Documents and Settings\Jacques\Bureau\random3.c
I see you have put it in a directory with spaces in the path. You can get away with this for compiuling a single file, but eventually, it will bite you when you compile a project. Avoid spaces. *Please*
:-)
Wayne
There are many relatively simple ways to "fake up" some "noise" for input into a randomizing scheme. One of the "cheapest" is user input, if the program can work that way.
There's a great deal of literature on the topic. Try a Google search on some key terms....
-- Jim.
the random number generation doesn't come from Windows but from the msvcrt library (which mingw uses, in all win32 versions); for me, the greatest defect it has is the small RAND_MAX
but you are also right: when you seed the generator, the first rand is too dependent on the seed
one solution is to call rand once or twice after srand, without using the values:
srand((unsigned) time(NULL)); //or shortly: srand(time(0));
rand();
rand();
and then you can do what you want
there are some random generators whose lower bits are "less random" (and in that case, you have to use the higher bits), but I think the one in msvcrt is not of that kind
if you want to know more about generating random numbers, read Knuth (The Art of Programming) vol. 2
Adrian
Incidentally, you might want to try out an implementation of the Mersenne Twister pseudo-random number algorithm from here:
http://www-personal.engin.umich.edu/~wagnerr/MersenneTwister.html
For some purposes, I use the Gnu Scientific Library (GSL) of random numbers. It has a large number of random distributions available. If you search the forum, you should find a couple of places where I talk about how to find it and set it up.
Wayne