DSPRelated.com
Forums

Generating Gaussian distributed random variable using C++

Started by YTach August 2, 2009
Hey Guys,

Is there a normal random generator function that can use to simulate
AWGN channel. I only know drand48() which is uniformally distributed.
but I need a white Gaussian random generator. Any hints?

I found this code below as a temporary solution for my case to
generate a normally distributed variable using drand48(), but I am
interested to know if there is an STL function or standard function
that I can use:

theta = drand48(); \\ A uniformly-distributed angle
U = drand48(); \\ A uniform variable to use in creating exponen-
tial sample D
D = -2*log(1-U); \\ D is an exponential random variable with
parameter 1/2
X = sqrt(D)*cos(theta); \\ X is Gaussian with mean 0, and vari-
ance = 1

<Source: https://engineering.purdue.edu/ece302/homeworks/HW7FA08Soln.pdf>
YTach  <y.tachwali@gmail.com> wrote:

>Is there a normal random generator function that can use to simulate >AWGN channel. I only know drand48() which is uniformally distributed. >but I need a white Gaussian random generator. Any hints?
>I found this code below as a temporary solution for my case to >generate a normally distributed variable using drand48(), but I am >interested to know if there is an STL function or standard function >that I can use:
>theta = drand48(); \\ A uniformly-distributed angle >U = drand48(); \\ A uniform variable to use in creating exponen- >tial sample D >D = -2*log(1-U); \\ D is an exponential random variable with >parameter 1/2 >X = sqrt(D)*cos(theta); \\ X is Gaussian with mean 0, and vari- >ance = 1
><Source: https://engineering.purdue.edu/ece302/homeworks/HW7FA08Soln.pdf>
I always use the following, the polar method from Knuth, but there is an identical description in Ross on google books: http://books.google.com/books?id=6h61E6XECfYC&pg=PA78&lpg=PA78&dq=polar+method&source=bl&ots=sTJ4vRLLoM&sig=epG1TW2SZm5iiTA8pdfCoiX0w2A&hl=en&ei=ji11SszoLYfUtgOA2KDYCA&sa=X&oi=book_result&ct=result&resnum=5#v=onepage&q=polar%20method&f=false You may wish to double-check my coding... Steve ********* cut here ******************** #include <cstdio> #include <cmath> #include <algorithm> double normal() { double v1, v2, s; const double x = 67108864.0; do { v1 = (((double)(std::rand() & 0x7ffffff) - x)) / x; v2 = (((double)(std::rand() & 0x7ffffff) - x)) / x; s = v1*v1+v2*v2; } while (s>=1.0); return(v1*std::sqrt(( -2.0 * std::log(s))/s)); }
>YTach <y.tachwali@gmail.com> wrote: > >>Is there a normal random generator function that can use to simulate >>AWGN channel. I only know drand48() which is uniformally distributed. >>but I need a white Gaussian random generator. Any hints? > >>I found this code below as a temporary solution for my case to >>generate a normally distributed variable using drand48(), but I am >>interested to know if there is an STL function or standard function >>that I can use: > >>theta = drand48(); \\ A uniformly-distributed angle >>U = drand48(); \\ A uniform variable to use in creating exponen- >>tial sample D >>D = -2*log(1-U); \\ D is an exponential random variable with >>parameter 1/2 >>X = sqrt(D)*cos(theta); \\ X is Gaussian with mean 0, and vari- >>ance = 1 > >><Source:
https://engineering.purdue.edu/ece302/homeworks/HW7FA08Soln.pdf>
> >I always use the following, the polar method from Knuth, but there >is an identical description in Ross on google books: > >http://books.google.com/books?id=6h61E6XECfYC&pg=PA78&lpg=PA78&dq=polar+method&source=bl&ots=sTJ4vRLLoM&sig=epG1TW2SZm5iiTA8pdfCoiX0w2A&hl=en&ei=ji11SszoLYfUtgOA2KDYCA&sa=X&oi=book_result&ct=result&resnum=5#v=onepage&q=polar%20method&f=false > >You may wish to double-check my coding... > >Steve > >********* cut here ******************** > > >#include <cstdio> >#include <cmath> >#include <algorithm> > >double normal() >{ >double v1, v2, s; >const double x = 67108864.0; > >do { > v1 = (((double)(std::rand() & 0x7ffffff) - x)) / x; > v2 = (((double)(std::rand() & 0x7ffffff) - x)) / x; > s = v1*v1+v2*v2; > } >while (s>=1.0); >return(v1*std::sqrt(( -2.0 * std::log(s))/s)); >}
Why make things so complex? :-\ The central limit theorem we learn in high school (unless your high school sucks) says the sum of a reasonably large bunch of random numbers looks awfully Gaussian. Summing 5 or 6 isn't too bad for some uses. 12 is a popular number to sum due to a misconception, but 12 is also a point at which the Gaussianess is good enough for most purposes. Of course, you will need to appropriately scale the sum. Steve
On 2 Aug, 06:24, YTach <y.tachw...@gmail.com> wrote:
> Hey Guys, > > Is there a normal random generator function that can use to simulate > AWGN channel. I only know drand48() which is uniformally distributed. > but I need a white Gaussian random generator. Any hints?
Rumour has it that there recently was added a standard library on random numbers to C++: http://www.codeguru.com/cpp/cpp/cpp_mfc/stl/article.php/c15319 The TR1 additions are very recent, so don't expect more than a few compilers to have these things installed. In the mean time, try out the Boost.random library, http://www.boost.org/doc/libs/1_39_0/libs/random/index.html You might want to ask about C++ technicalities in comp.lang.c++.moderated. Rune
On Aug 2, 2:04&#4294967295;am, "steveu" <ste...@coppice.org> wrote:

> > The central limit theorem we learn in high school (unless your high school > sucks) says the sum of a reasonably large bunch of random numbers looks > awfully Gaussian. Summing 5 or 6 isn't too bad for some uses. 12 is a > popular number to sum due to a misconception, but 12 is also a point at > which the Gaussianess is good enough for most purposes. Of course, you will > need to appropriately scale the sum.
If the above is what was taught to steveu in high school, then it is reasonable to conclude that his high school (or the state-mandated high school curriculum that his high school teacher was required to follow) sucks. If the above is what steveu remembers from the correct statement of the central limit theorem that he was taught in high school, then he obviously wasn't paying attention in class that day. Sheesh! --Dilip Sarwate

Steve Pope wrote:

> I always use the following, the polar method from Knuth, but there is > an identical description in Ross on google books: > > You may wish to double-check my coding...
1. You should not not assume that RAND_MAX = 0x7FFFFFFF. It could be anything else (like 0x7FFF) depending on the implementation. 2. Since you are calculating sqrt(log()), you need many random bits (~64) to represent the tail of the distribution. (1) and (2) are asking for the roll your own PRNG to be fed into the polar method. Vladimir Vassilevsky DSP and Mixed Signal Design Consultant http://www.abvolt.com
"steveu" <steveu@coppice.org> writes:
> [...] > The central limit theorem we learn in high school (unless your high school > sucks)
So, in your high school, the average student a) learns integral calculus, and b) learns how to use that calculus in other math and science topics? In the typical high schools here in the states, very few students make it to calculus in their senior year. At the end of that class, there is no time left to apply what they have learned to other coursework. I know the U.S. is behind, but I'd be suprised if they were *THAT* much behind. -- Randy Yates % "How's life on earth? Digital Signal Labs % ... What is it worth?" mailto://yates@ieee.org % 'Mission (A World Record)', http://www.digitalsignallabs.com % *A New World Record*, ELO
On 2 Aug, 15:32, "dvsarw...@yahoo.com" <dvsarw...@gmail.com> wrote:
> On Aug 2, 2:04&#4294967295;am, "steveu" <ste...@coppice.org> wrote: > > > > > The central limit theorem we learn in high school (unless your high school > > sucks) says the sum of a reasonably large bunch of random numbers looks > > awfully Gaussian. Summing 5 or 6 isn't too bad for some uses. 12 is a > > popular number to sum due to a misconception, but 12 is also a point at > > which the Gaussianess is good enough for most purposes. Of course, you will > > need to appropriately scale the sum. > > If the above is what was taught to steveu in high school, > then it is reasonable to conclude that his high school > (or the state-mandated high school curriculum &#4294967295;that his high > school teacher was required to follow) sucks. &#4294967295;If the above is > what steveu remembers from the correct statement of the > central limit theorem that he was taught in high school, then > he obviously wasn't paying attention in class that day. > > Sheesh!
What's the problem? That the sum of random variables tends towards a Gaussian dirstibution? Or the specific numbers? Rune
On Aug 2, 10:13&#4294967295;am, Rune Allnor <all...@tele.ntnu.no> asked:

> > What's the problem? That the sum of random variables tends > towards a Gaussian dirstibution?
Yes. The central limit theorem requires certain conditions on the random variables. It certainly is not true in all cases that "The central limit theorem ... <gratuitous comment deleted>.... says the sum of a reasonably large bunch of random numbers looks awfully Gaussian" as steveu stated. This point has been discussed previously in this newsgroup, and several people have noted, for example, that the sum of n Cauchy random variables is a (scaled) Cauchy random variable, and doesn't "look Gaussian".
> Or the specific numbers?
To a certain extent, yes. I don't know what misconception steveu was referring to when he wrote "12 is a popular number to sum due to a misconception" but 12 is often used because a random variable uniformly distributed on (0, 1) has variance 1/12. Thus the sum of 12 such independent uniform variates has variance 1. Subtracting off the mean (6), gives a zero-mean, unit variance random variable whose density is a good approximation to a unit Gaussian density. (One could, of course, sum together a different number of uniform variates, but then more complicated scaling is required.) **However**, the random variable thus generated (from the sum of 12 independent random variables) is limited to have values in the range (-6, 6) and is not necessarily of much help when (for example) **very small** error probabilities are to be determined via simulation: the error events in question might never occur during the simulation. --Dilip Sarwate
Vladimir Vassilevsky  <nospam@nowhere.com> wrote:

>Steve Pope wrote:
>> I always use the following, the polar method from Knuth, but there is >> an identical description in Ross on google books:
>1. You should not not assume that RAND_MAX = 0x7FFFFFFF. It could be >anything else (like 0x7FFF) depending on the implementation.
Correct. I use a version of rand() that is tried and true, not a library version.
>2. Since you are calculating sqrt(log()), you need many random bits >(~64) to represent the tail of the distribution.
>(1) and (2) are asking for the roll your own PRNG to be fed into the >polar method.
I agree. If you like, I'll post my local rand(), which was authored by a colleague about 20 years ago. I've done a number of statistical tests on the output of these generators. Steve