/*!\brief Ziggurat random number generator based on rejection sampling. It returns a pseudorandom normally distributed double number between -4.5 and 4.5*/
doubleziggurat()
{
returnNOR;
}
/*
@defgroup _gaussdouble Gaussian random number generator based on modified Box-Muller transformation.
...
...
@@ -227,58 +222,103 @@ double uniformrandom(void)
*/
/*!\brief Gaussian random number generator based on modified Box-Muller transformation.Returns a double-precision floating-point number. */
#define Ziggurat_SSE
#ifdef Ziggurat_SSE
doublegaussdouble(doublemean,doublevariance)
#define random_SSE
#ifdef random_SSE
doublegaussdouble(doublemean,doublevariance)//It is necessary to improve the function. However if we enable SSE the gain in time it is not too much.
//printf("normal random number %e, max %e, min %e\n",sqrt(variance)*gset + mean, max,min);
if(max<sqrt(variance)*gset+mean)
max=sqrt(variance)*gset+mean;
if(min>sqrt(variance)*gset+mean)
min=sqrt(variance)*gset+mean;
return(sqrt(variance)*gset+mean);
}
}
#else
doublegaussdouble(doublemean,doublevariance)
{
/*static int first_run;
static double sum;
static int count;
if (!first_run)
{
first_run=1;
sum=0;
count=0;
} */
staticintiset=0;
staticdoublegset;
doublefac,r,v1,v2;
staticdoublemax=-1000000;
staticdoublemin=1000000;
if(iset==0){
do{
/*count++;
clock_t start=clock();*/
v1=2.0*uniformrandom()-1.0;
/*clock_t stop=clock();
printf("UE_freq_channel time is %f s, AVERAGE time is %f s, count %d, sum %e\n",(float) (stop-start)/CLOCKS_PER_SEC,(float) (sum+stop-start)/(count*CLOCKS_PER_SEC),count,sum+stop-start);
sum=(sum+stop-start);*/
v2=2.0*uniformrandom()-1.0;
r=v1*v1+v2*v2;
//printf("Inside do: r %e\n",r);
}while(r>=1.0);
//printf("outside do: r %e\n",r);
fac=sqrt(-2.0*log(r)/r);
gset=v1*fac;
iset=1;
return(sqrt(variance)*v2*fac+mean);
}else{
iset=0;
//printf("normal random number %e, max %e, min %e\n",sqrt(variance)*gset + mean, max,min);