Contributor: RANDALL ELTON DING (* From: randyd@alpha2.csd.uwm.edu (Randall Elton Ding) >I a program I'm currently struggeling with, I need to get a random number >from a Gaussian distribution. Anybody got any ideas or anybody able to point >to something which does the job. This does a pretty good job of generating a gaussian random variable with mean `a` and standard deviation `d`. This program also does a graphic plot to demonstrate the function. First, here is the origional C source if the gaussian function which I transcribed to beloved pascal.. /* ------------------------------------------------ * * gaussian -- generates a gaussian random variable * * with mean a and standard deviation d * * ------------------------------------------------ */ double gaussian(a,d) double a,d; { static double t = 0.0; double x,v1,v2,r; if (t == 0) { do { v1 = 2.0 * rnd() - 1.0; v2 = 2.0 * rnd() - 1.0; r = v1 * v1 + v2 * v2; } while (r>=1.0); r = sqrt((-2.0*log(r))/r); t = v2*r; return(a+v1*r*d); } else { x = t; t = 0.0; return(a+x*d); } } * ---------------------------------------------------------------------- * now, the same thing in pascal * ---------------------------------------------------------------------- *) {$N+} program testgaussian; uses graph,crt; const bgipath = 'e:\bp\bgi'; procedure initbgi; var errcode,grdriver,grmode: integer; begin grdriver:= detect; grmode:= 0; initgraph (grdriver,grmode,bgipath); errcode:= graphresult; if errcode <> grok then begin writeln ('Graphics error: ',grapherrormsg (errcode)); halt (1); end; end; function rnd: double; { this isn't the best, but it works } var { returns a random number between 0 and 1 } i: integer; r: double; begin r:= 0; for i:= 1 to 15 do begin r:= r + random(10); r:= r/10; end; rnd:= r; end; function gaussian(a,d: double): double; { a is mean } const { d is standard deviation } t: double = 0; { pascal's equivalent to C's static variable } var x,v1,v2,r: double; begin if t=0 then begin repeat v1:= 2*rnd-1; v2:= 2*rnd-1; r:= v1*v1+v2*v2 until r<1; r:= sqrt((-2*ln(r))/r); t:= v2*r; gaussian:= a+v1*r*d; end else begin x:= t; t:= 0; gaussian:= a+x*d; end; end; procedure testplot; var x,mx,my,y1: word; y: array[1..999] of word; { ^^^ make this bigger if you have incredible graphics } begin initbgi; mx:= getmaxx+1; my:= getmaxy; fillchar(y,sizeof(y),#0); repeat x:= trunc(gaussian(mx/2,50)); y1:= y[x]; putpixel(x,my-y1,white); y[x]:= y1+1; until keypressed; closegraph; end; begin randomize; testplot; end.