Main Page   Namespace List   Class Hierarchy   Alphabetical List   Compound List   File List   Compound Members   File Members  

Rand.h

Go to the documentation of this file.
00001 #ifndef RAND_H
00002 #define RAND_H
00003 
00004 #include <cmath>
00005 #include <cstdlib>
00006 
00007 const int BIGPRIME = 899999963;
00008 
00009 class Rand {
00010         double c,cd,cm,u[97];
00011         int i97,j97 ;
00012         bool outputReady;
00013         double output;
00014 
00015 public:
00016         Rand(int seed=1) {
00017                 ranmarin(abs(seed%BIGPRIME));
00018                 outputReady=false;
00019         }
00020 
00021 /* Incompatible with Python?
00022         Rand() {
00023                 ranmarin(1);
00024                 outputReady=false;
00025         }
00026 */
00027 
00028         void seed(int seed) {
00029                 ranmarin(abs(seed%BIGPRIME));
00030                 outputReady=false;
00031         }
00032 
00033         double uniform()
00034         {
00035           double uni;
00036         
00037           uni=u[i97]-u[j97];
00038           if (uni<0.0) uni+=1.0;
00039           u[i97]=uni;
00040           if (--i97<0) i97=96;
00041           if (--j97<0) j97=96;
00042           c-=cd;
00043           if (c<0.0) c+=cm;
00044           uni-=c;
00045           if (uni<0.0) uni+=1.0;
00046           return(uni);
00047         }
00048 
00049         // Gives all numbers weighted equally, min and max inclusive
00050         int discrete(int min, int max)
00051         {
00052                 int ret= (int)(floor(uniform()*(max+1-min)+min));
00053 //              assert(ret<=max && ret>=min);
00054                 return ret;
00055         }
00056 
00057 
00058         double gaussian(double sd)
00059         {
00060                 double x,y,r,z;
00061                 if(outputReady)
00062                 {
00063                         outputReady = false;
00064                         return output*sd;
00065                 }
00066 
00067                 do
00068                 {
00069                         x=(uniform()*2.0)-1.0;
00070                         y=(uniform()*2.0)-1.0;
00071                         r=x*x+y*y;
00072                 } while (r>=1.0);
00073 
00074                 z=sqrt(-2.0*log(r)/r);
00075                 output = x*z;
00076                 outputReady=true;
00077                 return y*z*sd;
00078         }
00079 
00080 private:
00081         void ranmarin(int ijkl)
00082         {
00083           int i,ii,j,jj,k,l,m ;
00084           double s,t ;
00085 
00086       int ij=ijkl/30082;
00087       int kl=ijkl-30082*ij;
00088 
00089           i=((ij/177)%177)+2 ;
00090                 j=(ij%177)+2 ;
00091                 k=((kl/169)%178)+1 ;
00092                 l=kl%169 ;
00093                 for (ii=0;ii<97;ii++) {
00094             s=0.0 ;
00095                         t=0.5 ;
00096                         for (jj=0;jj<24;jj++) {
00097               m=(((i*j)%179)*k)%179 ;
00098                                 i=j;
00099                                 j=k;
00100                                 k=m;
00101                                 l=(53*l+1)%169;
00102                                 if (((l*m)%64)>=32) s+=t;
00103                                 t*=0.5;
00104                         }
00105                         u[ii]=s;
00106                 }
00107                 c=362436.0/16777216.0;
00108                 cd=7654321.0/16777216.0;
00109                 cm=16777213.0/16777216.0;
00110                 i97=96;
00111                 j97=32;
00112         }
00113             
00114 };      
00115 
00116 #endif

Generated on Mon Nov 3 09:38:11 2003 by doxygen1.2.14 written by Dimitri van Heesch, © 1997-2002