Generating random number between [-1, 1] in C?
Use -1+2*((float)rand())/RAND_MAX
rand()
generates integers in the range [0,RAND_MAX]
inclusive therefore, ((float)rand())/RAND_MAX
returns a floating-point number in [0,1]
. We get random numbers from [-1,1]
by adding it to -1
.
EDIT: (adding relevant portions of the comment section)
On the limitations of this method:
((float)rand())/RAND_MAX
returns a percentage (a fraction from 0 to 1). So since the range between -1 to 1 is 2 integers, I multiply that fraction by 2 and then add it to the minimum number you want, -1. This also tells you about the quality of your random numbers since you will only have RAND_MAX
unique random numbers.
If all you have is the Standard C library, then other people's answers are sensible. If you have POSIX functionality available to you, consider using the drand48() family of functions. In particular:
#define _XOPEN_SOURCE 600 /* Request non-standard functions */
#include <stdlib.h>
double f = +1.0 - 2.0 * drand48();
double g = -1.0 + 2.0 * drand48();
Note that the manual says:
The drand48() and erand48() functions shall return non-negative, double-precision, floating-point values, uniformly distributed over the interval [0.0,1.0).
If you strictly need [-1.0,+1.0]
(as opposed to [-1.0,+1.0)
), then you face a very delicate problem with how to extend the range.
The drand48()
functions give you considerably more randomness than the typical implementation of rand()
. However, if you need cryptographic randomness, none of these are appropriate; you need to look for 'cryptographically strong PRNG' (PRNG = pseudo-random number generator).
For starters, you'll need the C library function rand()
. This is in the stdlib.h
header file, so you should put:
#include <stdlib.h>
near the beginning of your code. rand()
will generate a random integer between zero and RAND_MAX
so dividing it by RAND_MAX / 2
will give you a number between zero and 2 inclusive. Subtract one, and you're onto your target range of -1 to 1.
However, if you simply do int n = rand() / (RAND_MAX / 2)
you will find you don't get the answer which you expect. This is because both rand()
and RAND_MAX / 2
are integers, so integer arithmetic is used. To stop this from happening, some people use a float cast, but I would recommend avoiding casts by multiplying by 1.0
.
You should also seed your random number generator using the srand()
function. In order to get a different result each time, people often seed the generator based on the clock time, by doing srand(time(0))
.
So, overall we have:
#include <stdlib.h>
srand(time(0);
double r = 1.0 * rand() / (RAND_MAX / 2) - 1;
I had a similar question a while back and thought that it might be more efficient to just generate the fractional part directly. I did some searching and came across an interesting fast floating point rand that doesn't use floating point division or multiplication or a int->float cast can be done with some intimate knowledge of the internal representation of a float:
float sfrand( void )
{
unsigned int a=(rand()<<16)|rand(); //we use the bottom 23 bits of the int, so one
//16 bit rand() won't cut it.
a=(a&0x007fffff) | 0x40000000;
return( *((float*)&a) - 3.0f );
}
The first part generates a random float from [2^1,2^2), subtract 3 and you have [-1, 1). This of course may be too intimate for some applications/developers but it was just what I was looking for. This mechanism works well for any range that is a power of 2 wide.