Boost logo

Boost Users :

From: Daniel Krügler (dsp_at_[hidden])
Date: 2007-04-26 03:38:59


Jeffrey Brent McBeth wrote:
> #include <boost/random.hpp>
> #include <iostream>
>
> int main(int argc, char *argv[])
> {
> boost::mt19937 eng;
> boost::normal_distribution<> norm(0,1);
> std::cout << norm(eng) << std::endl;
> }
>
>
> Gives me a NaN everytime. Looking at the code, it doesn't really surprise
> me, as
>
> _r1 = eng();
> _r2 = eng();
> _cached_rho = sqrt(-result_type(2)*log(result_type(1)-_r2));
>
> would only work if eng were in the range (0,1) with 0 being degenerate, and
> 1 being undefined.

IMO, you are totally right. normal_distribution<>::operator() should
accept any UniformRandomNumberGenerator, and boost::mt19937 fulfills
this requirement. The current implementation does not map the value's
of this generator into the feasible domain. I checked the current HEAD
which also has the same defect.

> Looking through the mt19937, that is returning a full UInt32.
> Perhaps those two eng() should be replaced by uniform_01?

I understand you to replace eng() by invokations of an uniform_01
engine created from the operator's Engine argument. If so, then the
proper mapping engine is *not* boost::uniform_01 but something like
boost::uniform_real. boost::uniform_01 is an engine adaptor that
*copies* it's constructor argument, therefore proper state transfer to
the engine argument would not take place. boost::uniform_real has the
wanted effect that it directly uses the given engine instance.

Since no-one has answered yet, I strongly recommend you to use the boost
bug tracking system to loudly signal this defect.

Greetings from Bremen,

Daniel Krügler


Boost-users list run by williamkempf at hotmail.com, kalb at libertysoft.com, bjorn.karlsson at readsoft.com, gregod at cs.rpi.edu, wekempf at cox.net