Geant4-11
Public Member Functions | Static Public Member Functions | Static Public Attributes | Protected Member Functions | Static Protected Member Functions | Protected Attributes | Static Protected Attributes | Private Member Functions | Static Private Member Functions | Private Attributes | Static Private Attributes
CLHEP::RandPoissonQ Class Reference

#include <RandPoissonQ.h>

Inheritance diagram for CLHEP::RandPoissonQ:
CLHEP::RandPoisson CLHEP::HepRandom

Public Member Functions

HepRandomEngineengine ()
 
long fire ()
 
long fire (double mean)
 
void fireArray (const int size, long *vect)
 
void fireArray (const int size, long *vect, double mean)
 
double flat ()
 
double flat (HepRandomEngine *theNewEngine)
 
void flatArray (const int size, double *vect)
 
void flatArray (HepRandomEngine *theNewEngine, const int size, double *vect)
 
std::istream & get (std::istream &is)
 
std::string name () const
 
double operator() ()
 
double operator() (double mean)
 
std::ostream & put (std::ostream &os) const
 
 RandPoissonQ (HepRandomEngine &anEngine, double b1=1.0)
 
 RandPoissonQ (HepRandomEngine *anEngine, double b1=1.0)
 
virtual ~RandPoissonQ ()
 

Static Public Member Functions

static int createInstance ()
 
static std::string distributionName ()
 
static HepRandomEnginegetTheEngine ()
 
static HepRandomgetTheGenerator ()
 
static long getTheSeed ()
 
static const long * getTheSeeds ()
 
static void getTheTableSeeds (long *seeds, int index)
 
static std::istream & restoreDistState (std::istream &is)
 
static void restoreEngineStatus (const char filename[]="Config.conf")
 
static std::istream & restoreFullState (std::istream &is)
 
static std::istream & restoreStaticRandomStates (std::istream &is)
 
static std::ostream & saveDistState (std::ostream &os)
 
static void saveEngineStatus (const char filename[]="Config.conf")
 
static std::ostream & saveFullState (std::ostream &os)
 
static std::ostream & saveStaticRandomStates (std::ostream &os)
 
static void setTheEngine (HepRandomEngine *theNewEngine)
 
static void setTheSeed (long seed, int lxr=3)
 
static void setTheSeeds (const long *seeds, int aux=-1)
 
static long shoot (double mean=1.0)
 
static long shoot (HepRandomEngine *anEngine, double mean=1.0)
 
static void shootArray (const int size, long *vect, double mean=1.0)
 
static void shootArray (HepRandomEngine *anEngine, const int size, long *vect, double mean=1.0)
 
static void showEngineStatus ()
 
static int tableBoundary ()
 

Static Public Attributes

static const double MAXIMUM_POISSON_DEVIATE = 2.0E9
 

Protected Member Functions

HepRandomEnginegetLocalEngine ()
 

Static Protected Member Functions

static double getMaxMean ()
 
static double getOldMean ()
 
static double * getPStatus ()
 
static void setOldMean (double val)
 
static void setPStatus (double sq, double alxm, double g1)
 

Protected Attributes

double defaultMean
 
double meanMax
 

Static Protected Attributes

static const long seedTable [215][2]
 

Private Member Functions

void setupForDefaultMu ()
 

Static Private Member Functions

static long poissonDeviateQuick (HepRandomEngine *e, double A0, double A1, double A2, double sig)
 
static long poissonDeviateQuick (HepRandomEngine *e, double mean)
 
static long poissonDeviateSmall (HepRandomEngine *e, double mean)
 

Private Attributes

double a0
 
double a1
 
double a2
 
std::shared_ptr< HepRandomEnginelocalEngine
 
double oldm
 
double sigma
 
double status [3]
 

Static Private Attributes

static const int BELOW = 30
 
static const int ENTRIES = 51
 
static const double FIRST_MU = 10
 
static const double LAST_MU = 95
 
static const double meanMax_st = 2.0E9
 
static CLHEP_THREAD_LOCAL double oldm_st = -1.0
 
static const double S = 5
 
static CLHEP_THREAD_LOCAL double status_st [3] = {0., 0., 0.}
 

Detailed Description

Author

Definition at line 31 of file RandPoissonQ.h.

Constructor & Destructor Documentation

◆ RandPoissonQ() [1/2]

CLHEP::RandPoissonQ::RandPoissonQ ( HepRandomEngine anEngine,
double  b1 = 1.0 
)
inline

◆ RandPoissonQ() [2/2]

CLHEP::RandPoissonQ::RandPoissonQ ( HepRandomEngine anEngine,
double  b1 = 1.0 
)
inline

◆ ~RandPoissonQ()

CLHEP::RandPoissonQ::~RandPoissonQ ( )
virtual

Definition at line 82 of file RandPoissonQ.cc.

82 {
83}

Member Function Documentation

◆ createInstance()

int CLHEP::HepRandom::createInstance ( )
staticinherited

◆ distributionName()

static std::string CLHEP::RandPoissonQ::distributionName ( )
inlinestatic

Definition at line 101 of file RandPoissonQ.h.

101{return "RandPoissonQ";}

◆ engine()

HepRandomEngine & CLHEP::RandPoissonQ::engine ( )
virtual

Reimplemented from CLHEP::RandPoisson.

Definition at line 52 of file RandPoissonQ.cc.

52{return RandPoisson::engine();}
HepRandomEngine & engine()
Definition: RandPoisson.cc:38

References CLHEP::RandPoisson::engine().

◆ fire() [1/2]

long CLHEP::RandPoissonQ::fire ( )

Definition at line 135 of file RandPoissonQ.cc.

135 {
136 if ( defaultMean < LAST_MU + S ) {
138 } else {
140 }
141} // fire()
static const double S
Definition: RandPoissonQ.h:144
static long poissonDeviateQuick(HepRandomEngine *e, double mean)
static const double LAST_MU
Definition: RandPoissonQ.h:143
static long poissonDeviateSmall(HepRandomEngine *e, double mean)
HepRandomEngine * getLocalEngine()

References a0, a1, a2, CLHEP::RandPoisson::defaultMean, CLHEP::RandPoisson::getLocalEngine(), LAST_MU, poissonDeviateQuick(), poissonDeviateSmall(), S, and sigma.

Referenced by fireArray(), and operator()().

◆ fire() [2/2]

long CLHEP::RandPoissonQ::fire ( double  mean)

Definition at line 131 of file RandPoissonQ.cc.

131 {
132 return shoot(getLocalEngine(), mean);
133}
static long shoot(double mean=1.0)

References CLHEP::RandPoisson::getLocalEngine(), and shoot().

◆ fireArray() [1/2]

void CLHEP::RandPoissonQ::fireArray ( const int  size,
long *  vect 
)

Definition at line 187 of file RandPoissonQ.cc.

187 {
188 for( long* v = vect; v != vect + size; ++v )
189 *v = fire( defaultMean );
190}

References CLHEP::RandPoisson::defaultMean, and fire().

◆ fireArray() [2/2]

void CLHEP::RandPoissonQ::fireArray ( const int  size,
long *  vect,
double  mean 
)

Definition at line 182 of file RandPoissonQ.cc.

182 {
183 for( long* v = vect; v != vect + size; ++v )
184 *v = fire( m );
185}
static constexpr double m

References fire(), and CLHEP::m.

◆ flat() [1/2]

double CLHEP::HepRandom::flat ( )
inherited

◆ flat() [2/2]

double CLHEP::HepRandom::flat ( HepRandomEngine theNewEngine)
inlineinherited

◆ flatArray() [1/2]

void CLHEP::HepRandom::flatArray ( const int  size,
double *  vect 
)
inherited

◆ flatArray() [2/2]

void CLHEP::HepRandom::flatArray ( HepRandomEngine theNewEngine,
const int  size,
double *  vect 
)
inlineinherited

◆ get()

std::istream & CLHEP::RandPoissonQ::get ( std::istream &  is)
virtual

Reimplemented from CLHEP::RandPoisson.

Definition at line 574 of file RandPoissonQ.cc.

574 {
575 std::string inName;
576 is >> inName;
577 if (inName != name()) {
578 is.clear(std::ios::badbit | is.rdstate());
579 std::cerr << "Mismatch when expecting to read state of a "
580 << name() << " distribution\n"
581 << "Name found was " << inName
582 << "\nistream is left in the badbit state\n";
583 return is;
584 }
585 if (possibleKeywordInput(is, "Uvec", a0)) {
586 std::vector<unsigned long> t(2);
587 is >> a0 >> t[0] >> t[1]; a0 = DoubConv::longs2double(t);
588 is >> a1 >> t[0] >> t[1]; a1 = DoubConv::longs2double(t);
589 is >> a2 >> t[0] >> t[1]; a2 = DoubConv::longs2double(t);
590 is >> sigma >> t[0] >> t[1]; sigma = DoubConv::longs2double(t);
592 return is;
593 }
594 // is >> a0 encompassed by possibleKeywordInput
595 is >> a1 >> a2 >> sigma;
597 return is;
598}
static double longs2double(const std::vector< unsigned long > &v)
Definition: DoubConv.cc:110
std::string name() const
Definition: RandPoissonQ.cc:51
std::istream & get(std::istream &is)
Definition: RandPoisson.cc:304
bool possibleKeywordInput(IS &is, const std::string &key, T &t)
Definition: RandomEngine.h:166

References a0, a1, a2, CLHEP::RandPoisson::get(), CLHEP::DoubConv::longs2double(), name(), CLHEP::possibleKeywordInput(), and sigma.

◆ getLocalEngine()

HepRandomEngine * CLHEP::RandPoisson::getLocalEngine ( )
inlineprotectedinherited

Referenced by fire().

◆ getMaxMean()

static double CLHEP::RandPoisson::getMaxMean ( )
inlinestaticprotectedinherited

Definition at line 103 of file RandPoisson.h.

103{return meanMax_st;}
static const double meanMax_st
Definition: RandPoisson.h:123

References CLHEP::RandPoisson::meanMax_st.

Referenced by CLHEP::RandPoisson::fire(), and CLHEP::RandPoisson::shoot().

◆ getOldMean()

static double CLHEP::RandPoisson::getOldMean ( )
inlinestaticprotectedinherited

Definition at line 101 of file RandPoisson.h.

101{return oldm_st;}
static CLHEP_THREAD_LOCAL double oldm_st
Definition: RandPoisson.h:122

References CLHEP::RandPoisson::oldm_st.

Referenced by CLHEP::RandPoisson::shoot().

◆ getPStatus()

static double * CLHEP::RandPoisson::getPStatus ( )
inlinestaticprotectedinherited

Definition at line 107 of file RandPoisson.h.

107{return status_st;}
static CLHEP_THREAD_LOCAL double status_st[3]
Definition: RandPoisson.h:121

References CLHEP::RandPoisson::status_st.

Referenced by CLHEP::RandPoisson::shoot().

◆ getTheEngine()

HepRandomEngine * CLHEP::HepRandom::getTheEngine ( )
staticinherited

◆ getTheGenerator()

HepRandom * CLHEP::HepRandom::getTheGenerator ( )
staticinherited

◆ getTheSeed()

long CLHEP::HepRandom::getTheSeed ( )
staticinherited

◆ getTheSeeds()

const long * CLHEP::HepRandom::getTheSeeds ( )
staticinherited

◆ getTheTableSeeds()

void CLHEP::HepRandom::getTheTableSeeds ( long *  seeds,
int  index 
)
staticinherited

Definition at line 254 of file Random.cc.

255{
256 if ((index >= 0) && (index < 215)) {
257 seeds[0] = seedTable[index][0];
258 seeds[1] = seedTable[index][1];
259 }
260 else seeds = NULL;
261}
static const long seedTable[215][2]
Definition: Random.h:156

Referenced by CLHEP::HepJamesRandom::HepJamesRandom(), CLHEP::MTwistEngine::MTwistEngine(), CLHEP::RanecuEngine::RanecuEngine(), CLHEP::Ranlux64Engine::Ranlux64Engine(), CLHEP::RanluxEngine::RanluxEngine(), and CLHEP::RanecuEngine::setSeed().

◆ name()

std::string CLHEP::RandPoissonQ::name ( ) const
virtual

Reimplemented from CLHEP::RandPoisson.

Definition at line 51 of file RandPoissonQ.cc.

51{return "RandPoissonQ";}

Referenced by source.g4viscp.G4Scene::create_scene(), get(), mcscore.MCParticle::printout(), put(), and source.g4viscp.G4Scene::update_scene().

◆ operator()() [1/2]

double CLHEP::RandPoissonQ::operator() ( )
virtual

Reimplemented from CLHEP::RandPoisson.

Definition at line 123 of file RandPoissonQ.cc.

123 {
124 return (double) fire();
125}

References fire().

◆ operator()() [2/2]

double CLHEP::RandPoissonQ::operator() ( double  mean)

Definition at line 127 of file RandPoissonQ.cc.

127 {
128 return (double) fire(mean);
129}

References fire().

◆ poissonDeviateQuick() [1/2]

long CLHEP::RandPoissonQ::poissonDeviateQuick ( HepRandomEngine e,
double  A0,
double  A1,
double  A2,
double  sig 
)
staticprivate

Definition at line 219 of file RandPoissonQ.cc.

220 {
221//
222// Quick Poisson deviate algorithm used by quick for large mu:
223//
224// The principle: For very large mu, a poisson distribution can be approximated
225// by a gaussian: return the integer part of mu + .5 + g where g is a unit
226// normal. However, this yelds a miserable approximation at values as
227// "large" as 100. The primary problem is that the poisson distribution is
228// supposed to have a skew of 1/mu**2, and the zero skew of the Guassian
229// leads to errors of order as big as 1/mu**2.
230//
231// We substitute for the gaussian a quadratic function of that gaussian random.
232// The expression looks very nearly like mu + .5 - 1/6 + g + g**2/(6*mu).
233// The small positive quadratic term causes the resulting variate to have
234// a positive skew; the -1/6 constant term is there to correct for this bias
235// in the mean. By adjusting these two and the linear term, we can match the
236// first three moments to high accuracy in 1/mu.
237//
238// The sigma used is not precisely sqrt(mu) since a rounded-off Gaussian
239// has a second moment which is slightly larger than that of the Gaussian.
240// To compensate, sig is multiplied by a factor which is slightly less than 1.
241
242 // double g = RandGauss::shootQuick( e ); // TEMPORARY MOD:
243 double g = RandGaussQ::shoot( e ); // Unit normal
244 g *= sig;
245 double p = A2*g*g + A1*g + A0;
246 if ( p < 0 ) return 0; // Shouldn't ever possibly happen since
247 // mean should not be less than 100, but
248 // we check due to paranoia.
250
251 return long(p);
252
253} // poissonDeviateQuick ()
static double shoot()
static const double MAXIMUM_POISSON_DEVIATE
Definition: RandPoissonQ.h:108
static constexpr double g

References CLHEP::g, MAXIMUM_POISSON_DEVIATE, and CLHEP::RandGaussQ::shoot().

◆ poissonDeviateQuick() [2/2]

long CLHEP::RandPoissonQ::poissonDeviateQuick ( HepRandomEngine e,
double  mean 
)
staticprivate

Definition at line 195 of file RandPoissonQ.cc.

195 {
196
197 // Compute the coefficients defining the quadratic transformation from a
198 // Gaussian to a Poisson:
199
200 double sig2 = mu * (.9998654 - .08346/mu);
201 double sig = std::sqrt(sig2);
202 // The multiplier corrects for fact that discretization of the form
203 // [gaussian+.5] increases the second moment by a small amount.
204
205 double t = 1./sig2;
206
207 double sa2 = t*(1./6.) + t*t*(1./324.);
208 double sa1 = std::sqrt (1-2*sa2*sa2*sig2);
209 double sa0 = mu + .5 - sig2 * sa2;
210
211 // The formula will be sa0 + sa1*x + sa2*x*x where x has sigma of sq.
212 // The coeffeicients are chosen to match the first THREE moments of the
213 // true Poisson distribution.
214
215 return poissonDeviateQuick ( e, sa0, sa1, sa2, sig );
216}

References poissonDeviateQuick().

Referenced by fire(), poissonDeviateQuick(), and shoot().

◆ poissonDeviateSmall()

long CLHEP::RandPoissonQ::poissonDeviateSmall ( HepRandomEngine e,
double  mean 
)
staticprivate

Definition at line 257 of file RandPoissonQ.cc.

257 {
258 long N1;
259 long N2;
260 // The following are for later use to form a secondary random s:
261 double rRange; // This will hold the interval between cdf for the
262 // computed N1 and cdf for N1+1.
263 double rRemainder = 0; // This will hold the length into that interval.
264
265 // Coming in, mean should not be more than LAST_MU + S. However, we will
266 // be paranoid and test for this:
267
268 if ( mean > LAST_MU + S ) {
269 return RandPoisson::shoot(e, mean);
270 }
271
272 if (mean <= 0) {
273 return 0; // Perhaps we ought to balk harder here!
274 }
275
276 // >>> 1 <<<
277 // Generate the first random, which we always will need.
278
279 double r = e->flat();
280
281 // >>> 2 <<<
282 // For small mean, below the start of the tables,
283 // do the series for cdf directly.
284
285 // In this case, since we know the series will terminate relatively quickly,
286 // almost alwaye use a precomputed 1/N array without fear of overrunning it.
287
288 static const double oneOverN[50] =
289 { 0, 1., 1/2., 1/3., 1/4., 1/5., 1/6., 1/7., 1/8., 1/9.,
290 1/10., 1/11., 1/12., 1/13., 1/14., 1/15., 1/16., 1/17., 1/18., 1/19.,
291 1/20., 1/21., 1/22., 1/23., 1/24., 1/25., 1/26., 1/27., 1/28., 1/29.,
292 1/30., 1/31., 1/32., 1/33., 1/34., 1/35., 1/36., 1/37., 1/38., 1/39.,
293 1/40., 1/41., 1/42., 1/43., 1/44., 1/45., 1/46., 1/47., 1/48., 1/49. };
294
295
296 if ( mean < FIRST_MU ) {
297
298 long N = 0;
299 double term = std::exp(-mean);
300 double cdf = term;
301
302 if ( r < (1 - 1.0E-9) ) {
303 //
304 // **** This is a normal path: ****
305 //
306 // Except when r is very close to 1, it is certain that we will exceed r
307 // before the 30-th term in the series, so a simple while loop is OK.
308 const double* oneOverNptr = oneOverN;
309 while( cdf <= r ) {
310 N++ ;
311 oneOverNptr++;
312 term *= ( mean * (*oneOverNptr) );
313 cdf += term;
314 }
315 return N;
316 //
317 // **** ****
318 //
319 } else { // r is almost 1...
320 // For r very near to 1 we would have to check that we don't fall
321 // off the end of the table of 1/N. Since this is very rare, we just
322 // ignore the table and do the identical while loop, using explicit
323 // division.
324 double cdf0;
325 while ( cdf <= r ) {
326 N++ ;
327 term *= ( mean / N );
328 cdf0 = cdf;
329 cdf += term;
330 if (cdf == cdf0) break; // Can't happen, but just in case...
331 }
332 return N;
333 } // end of if ( r compared to (1 - 1.0E-9) )
334
335 } // End of the code for mean < FIRST_MU
336
337 // >>> 3 <<<
338 // Find the row of the tables corresponding to the highest tabulated mu
339 // which is no greater than our actual mean.
340
341 int rowNumber = int((mean - FIRST_MU)/S);
342 const double * cdfs = &poissonTables [rowNumber*ENTRIES];
343 double mu = FIRST_MU + rowNumber*S;
344 double deltaMu = mean - mu;
345 int Nmin = int(mu - BELOW);
346 if (Nmin < 1) Nmin = 1;
347 int Nmax = Nmin + (ENTRIES - 1);
348
349
350 // >>> 4 <<<
351 // If r is less that the smallest entry in the row, then
352 // generate the deviate directly from the series.
353
354 if ( r < cdfs[0] ) {
355
356 // In this case, we are tempted to use the actual mean, and not
357 // generate a second deviate to account for the leftover part mean - mu.
358 // That would be an error, generating a distribution with enough excess
359 // at Nmin + (mean-mu)/2 to be detectable in 4,000,000 trials.
360
361 // Since this case is very rare (never more than .2% of the r values)
362 // and can happen where N will be large (up to 65 for the mu=95 row)
363 // we use explicit division so as to avoid having to worry about running
364 // out of oneOverN table.
365
366 long N = 0;
367 double term = std::exp(-mu);
368 double cdf = term;
369 double cdf0;
370
371 while(cdf <= r) {
372 N++ ;
373 term *= ( mu / N );
374 cdf0 = cdf;
375 cdf += term;
376 if (cdf == cdf0) break; // Can't happen, but just in case...
377 }
378 N1 = N;
379 // std::cout << r << " " << N << " ";
380 // DBG_small = true;
381 rRange = 0; // In this case there is always a second r needed
382
383 } // end of small-r case
384
385
386 // >>> 5 <<<
387 // Assuming r lies within the scope of the row for this mu, find the
388 // largest entry not greater than r. N1 is the N corresponding to the
389 // index a.
390
391 else if ( r < cdfs[ENTRIES-1] ) { // r is also >= cdfs[0]
392
393 //
394 // **** This is the normal code path ****
395 //
396
397 int a = 0; // Highest value of index such that cdfs[a]
398 // is known NOT to be greater than r.
399 int b = ENTRIES - 1; // Lowest value of index such that cdfs[b] is
400 // known to exeed r.
401
402 while (b != (a+1) ) {
403 int c = (a+b+1)>>1;
404 if (r > cdfs[c]) {
405 a = c;
406 } else {
407 b = c;
408 }
409 }
410
411 N1 = Nmin + a;
412 rRange = cdfs[a+1] - cdfs[a];
413 rRemainder = r - cdfs[a];
414
415 //
416 // **** ****
417 //
418
419 } // end of medium-r (normal) case
420
421
422 // >>> 6 <<<
423 // If r exceeds the greatest entry in the table for this mu, then start
424 // from that cdf, and use the series to compute from there until r is
425 // exceeded.
426
427 else { // if ( r >= cdfs[ENTRIES-1] ) {
428
429 // Here, division must be done explicitly, and we must also protect against
430 // roundoff preventing termination.
431
432 //
433 //+++ cdfs[ENTRIES-1] is exp(-mu) sum (mu**m/m! , m=0 to Nmax)
434 //+++ (where Nmax = mu - BELOW + ENTRIES - 1)
435 //+++ cdfs[ENTRIES-1]-cdfs[ENTRIES-2] is exp(-mu) mu**(Nmax)/(Nmax)!
436 //+++ If the sum up to k-1 <= r < sum up to k, then N = k-1
437 //+++ Consider k = Nmax in the above statement:
438 //+++ If cdfs[ENTRIES-2] <= r < cdfs[ENTRIES-1], N would be Nmax-1
439 //+++ But here r >= cdfs[ENTRIES-1] so N >= Nmax
440 //
441
442 // Erroneous:
443 //+++ cdfs[ENTRIES-1] is exp(-mu) sum (mu**m/m! , m=0 to Nmax-1)
444 //+++ cdfs[ENTRIES-1]-cdfs[ENTRIES-2] is exp(-mu) mu**(Nmax-1)/(Nmax-1)!
445 //+++ If a sum up to k-1 <= r < sum up to k, then N = k-1
446 //+++ So if cdfs[ENTRIES-1] were > r, N would be Nmax-1 (or less)
447 //+++ But here r >= cdfs[ENTRIES-1] so N >= Nmax
448 //
449
450 // std::cout << "r = " << r << " mu = " << mu << "\n";
451 long N = Nmax -1;
452 double cdf = cdfs[ENTRIES-1];
453 double term = cdf - cdfs[ENTRIES-2];
454 double cdf0;
455 while(cdf <= r) {
456 N++ ;
457 // std::cout << " N " << N << " term " <<
458 // term << " cdf " << cdf << "\n";
459 term *= ( mu / N );
460 cdf0 = cdf;
461 cdf += term;
462 if (cdf == cdf0) break; // If term gets so small cdf stops increasing,
463 // terminate using that value of N since we
464 // would never reach r.
465 }
466 N1 = N;
467 rRange = 0; // We can't validly omit the second true random
468
469 // N = Nmax -1;
470 // cdf = cdfs[ENTRIES-1];
471 // term = cdf - cdfs[ENTRIES-2];
472 // for (int isxz=0; isxz < 100; isxz++) {
473 // N++ ;
474 // term *= ( mu / N );
475 // cdf0 = cdf;
476 // cdf += term;
477 // }
478 // std::cout.precision(20);
479 // std::cout << "Final sum is " << cdf << "\n";
480
481 } // end of large-r case
482
483
484
485 // >>> 7 <<<
486 // Form a second random, s, based on the position of r within the range
487 // of this table entry to the next entry.
488
489 // However, if this range is very small, then we lose too many bits of
490 // randomness. In that situation, we generate a second random for s.
491
492 double s;
493
494 static const double MINRANGE = .01; // Sacrifice up to two digits of
495 // randomness when using r to produce
496 // a second random s. Leads to up to
497 // .09 extra randoms each time.
498
499 if ( rRange > MINRANGE ) {
500 //
501 // **** This path taken 90% of the time ****
502 //
503 s = rRemainder / rRange;
504 } else {
505 s = e->flat(); // extra true random needed about one time in 10.
506 }
507
508 // >>> 8 <<<
509 // Use the direct summation method to form a second poisson deviate N2
510 // from deltaMu and s.
511
512 N2 = 0;
513 double term = std::exp(-deltaMu);
514 double cdf = term;
515
516 if ( s < (1 - 1.0E-10) ) {
517 //
518 // This is the normal path:
519 //
520 const double* oneOverNptr = oneOverN;
521 while( cdf <= s ) {
522 N2++ ;
523 oneOverNptr++;
524 term *= ( deltaMu * (*oneOverNptr) );
525 cdf += term;
526 }
527 } else { // s is almost 1...
528 while( cdf <= s ) {
529 N2++ ;
530 term *= ( deltaMu / N2 );
531 cdf += term;
532 }
533 } // end of if ( s compared to (1 - 1.0E-10) )
534
535 // >>> 9 <<<
536 // The result is the sum of those two deviates
537
538 // if (DBG_small) {
539 // std::cout << N2 << " " << N1+N2 << "\n";
540 // DBG_small = false;
541 // }
542
543 return N1 + N2;
544
545} // poissonDeviate()
static const double FIRST_MU
Definition: RandPoissonQ.h:142
static const int ENTRIES
Definition: RandPoissonQ.h:146
static const int BELOW
Definition: RandPoissonQ.h:145
static long shoot(double mean=1.0)
Definition: RandPoisson.cc:93
static const double poissonTables[51 *((95-10)/5+1)]
Definition: RandPoissonQ.cc:74
static constexpr double s

References BELOW, ENTRIES, FIRST_MU, CLHEP::HepRandomEngine::flat(), LAST_MU, CLHEP::poissonTables, S, CLHEP::s, and CLHEP::RandPoisson::shoot().

Referenced by fire(), and shoot().

◆ put()

std::ostream & CLHEP::RandPoissonQ::put ( std::ostream &  os) const
virtual

Reimplemented from CLHEP::RandPoisson.

Definition at line 547 of file RandPoissonQ.cc.

547 {
548 int pr=os.precision(20);
549 std::vector<unsigned long> t(2);
550 os << " " << name() << "\n";
551 os << "Uvec" << "\n";
553 os << a0 << " " << t[0] << " " << t[1] << "\n";
555 os << a1 << " " << t[0] << " " << t[1] << "\n";
557 os << a2 << " " << t[0] << " " << t[1] << "\n";
559 os << sigma << " " << t[0] << " " << t[1] << "\n";
561 os.precision(pr);
562 return os;
563#ifdef REMOVED
564 int pr=os.precision(20);
565 os << " " << name() << "\n";
566 os << a0 << " " << a1 << " " << a2 << "\n";
567 os << sigma << "\n";
569 os.precision(pr);
570 return os;
571#endif
572}
static std::vector< unsigned long > dto2longs(double d)
Definition: DoubConv.cc:94
std::ostream & put(std::ostream &os) const
Definition: RandPoisson.cc:283

References a0, a1, a2, CLHEP::DoubConv::dto2longs(), name(), CLHEP::RandPoisson::put(), and sigma.

◆ restoreDistState()

static std::istream & CLHEP::HepRandom::restoreDistState ( std::istream &  is)
inlinestaticinherited

Definition at line 136 of file Random.h.

136{return is;}

◆ restoreEngineStatus()

void CLHEP::HepRandom::restoreEngineStatus ( const char  filename[] = "Config.conf")
staticinherited

Definition at line 283 of file Random.cc.

284{
285 theDefaults().theEngine->restoreStatus( filename );
286}

References CLHEP::anonymous_namespace{Random.cc}::theDefaults(), and CLHEP::anonymous_namespace{Random.cc}::defaults::theEngine.

◆ restoreFullState()

std::istream & CLHEP::HepRandom::restoreFullState ( std::istream &  is)
staticinherited

Definition at line 293 of file Random.cc.

293 {
294 is >> *getTheEngine();
295 return is;
296}
static HepRandomEngine * getTheEngine()
Definition: Random.cc:268

Referenced by CLHEP::RandFlat::restoreFullState(), and CLHEP::RandGauss::restoreFullState().

◆ restoreStaticRandomStates()

std::istream & CLHEP::HepRandom::restoreStaticRandomStates ( std::istream &  is)
staticinherited

Definition at line 302 of file Random.cc.

302 {
304}
static std::istream & restore(std::istream &is)

References CLHEP::StaticRandomStates::restore().

◆ saveDistState()

static std::ostream & CLHEP::HepRandom::saveDistState ( std::ostream &  os)
inlinestaticinherited

Definition at line 133 of file Random.h.

133{return os;}

◆ saveEngineStatus()

void CLHEP::HepRandom::saveEngineStatus ( const char  filename[] = "Config.conf")
staticinherited

◆ saveFullState()

std::ostream & CLHEP::HepRandom::saveFullState ( std::ostream &  os)
staticinherited

◆ saveStaticRandomStates()

std::ostream & CLHEP::HepRandom::saveStaticRandomStates ( std::ostream &  os)
staticinherited

Definition at line 298 of file Random.cc.

298 {
299 return StaticRandomStates::save(os);
300}
static std::ostream & save(std::ostream &os)

References CLHEP::StaticRandomStates::save().

◆ setOldMean()

static void CLHEP::RandPoisson::setOldMean ( double  val)
inlinestaticprotectedinherited

Definition at line 105 of file RandPoisson.h.

105{oldm_st = val;}

References CLHEP::RandPoisson::oldm_st.

Referenced by CLHEP::RandPoisson::shoot().

◆ setPStatus()

static void CLHEP::RandPoisson::setPStatus ( double  sq,
double  alxm,
double  g1 
)
inlinestaticprotectedinherited

Definition at line 109 of file RandPoisson.h.

109 {
110 status_st[0] = sq; status_st[1] = alxm; status_st[2] = g1;
111 }

References CLHEP::RandPoisson::status_st.

Referenced by CLHEP::RandPoisson::shoot().

◆ setTheEngine()

void CLHEP::HepRandom::setTheEngine ( HepRandomEngine theNewEngine)
staticinherited

Definition at line 273 of file Random.cc.

274{
275 theDefaults().theEngine.reset( theNewEngine, do_nothing_deleter() );
276}

References CLHEP::anonymous_namespace{Random.cc}::theDefaults(), and CLHEP::anonymous_namespace{Random.cc}::defaults::theEngine.

Referenced by CLHEP::StaticRandomStates::restore().

◆ setTheSeed()

void CLHEP::HepRandom::setTheSeed ( long  seed,
int  lxr = 3 
)
staticinherited

Definition at line 234 of file Random.cc.

235{
236 theDefaults().theEngine->setSeed(seed,lux);
237}
static constexpr double lux

References CLHEP::lux, CLHEP::anonymous_namespace{Random.cc}::theDefaults(), and CLHEP::anonymous_namespace{Random.cc}::defaults::theEngine.

◆ setTheSeeds()

void CLHEP::HepRandom::setTheSeeds ( const long *  seeds,
int  aux = -1 
)
staticinherited

◆ setupForDefaultMu()

void CLHEP::RandPoissonQ::setupForDefaultMu ( )
private

Definition at line 85 of file RandPoissonQ.cc.

85 {
86
87 // The following are useful for quick approximation, for large mu
88
89 double sig2 = defaultMean * (.9998654 - .08346/defaultMean);
90 sigma = std::sqrt(sig2);
91 // sigma for the Guassian which approximates the Poisson -- naively
92 // sqrt (defaultMean).
93 //
94 // The multiplier corrects for fact that discretization of the form
95 // [gaussian+.5] increases the second moment by a small amount.
96
97 double t = 1./(sig2);
98
99 a2 = t/6 + t*t/324;
100 a1 = std::sqrt (1-2*a2*a2*sig2);
101 a0 = defaultMean + .5 - sig2 * a2;
102
103 // The formula will be a0 + a1*x + a2*x*x where x has 2nd moment of sigma.
104 // The coeffeicients are chosen to match the first THREE moments of the
105 // true Poisson distribution.
106 //
107 // Actually, if the correction for discretization were not needed, then
108 // a2 could be taken one order higher by adding t*t*t/5832. However,
109 // the discretization correction is not perfect, leading to inaccuracy
110 // on the order to 1/mu**2, so adding a third term is overkill.
111
112} // setupForDefaultMu()

References a0, a1, a2, CLHEP::RandPoisson::defaultMean, and sigma.

◆ shoot() [1/2]

long CLHEP::RandPoissonQ::shoot ( double  mean = 1.0)
static

Definition at line 119 of file RandPoissonQ.cc.

119 {
120 return shoot(getTheEngine(), xm);
121}

References CLHEP::HepRandom::getTheEngine(), and shoot().

Referenced by fire(), shoot(), and shootArray().

◆ shoot() [2/2]

long CLHEP::RandPoissonQ::shoot ( HepRandomEngine anEngine,
double  mean = 1.0 
)
static

Definition at line 143 of file RandPoissonQ.cc.

143 {
144
145 // The following variables, static to this method, apply to the
146 // last time a large mean was supplied; they obviate certain calculations
147 // if consecutive calls use the same mean.
148
149 static CLHEP_THREAD_LOCAL double lastLargeMean = -1.; // Mean from previous shoot
150 // requiring poissonDeviateQuick()
151 static CLHEP_THREAD_LOCAL double lastA0;
152 static CLHEP_THREAD_LOCAL double lastA1;
153 static CLHEP_THREAD_LOCAL double lastA2;
154 static CLHEP_THREAD_LOCAL double lastSigma;
155
156 if ( mean < LAST_MU + S ) {
157 return poissonDeviateSmall ( anEngine, mean );
158 } else {
159 if ( mean != lastLargeMean ) {
160 // Compute the coefficients defining the quadratic transformation from a
161 // Gaussian to a Poisson for this mean. Also save these for next time.
162 double sig2 = mean * (.9998654 - .08346/mean);
163 lastSigma = std::sqrt(sig2);
164 double t = 1./sig2;
165 lastA2 = t*(1./6.) + t*t*(1./324.);
166 lastA1 = std::sqrt (1-2*lastA2*lastA2*sig2);
167 lastA0 = mean + .5 - sig2 * lastA2;
168 }
169 return poissonDeviateQuick ( anEngine, lastA0, lastA1, lastA2, lastSigma );
170 }
171
172} // shoot (anEngine, mean)
#define CLHEP_THREAD_LOCAL
Definition: thread_local.h:13

References CLHEP_THREAD_LOCAL, LAST_MU, poissonDeviateQuick(), poissonDeviateSmall(), and S.

◆ shootArray() [1/2]

void CLHEP::RandPoissonQ::shootArray ( const int  size,
long *  vect,
double  mean = 1.0 
)
static

Definition at line 174 of file RandPoissonQ.cc.

174 {
175 for( long* v = vect; v != vect + size; ++v )
176 *v = shoot(m);
177 // Note: We could test for m > 100, and if it is, precompute a0, a1, a2,
178 // and sigma and call the appropriate form of poissonDeviateQuick.
179 // But since those are cached anyway, not much time would be saved.
180}

References CLHEP::m, and shoot().

◆ shootArray() [2/2]

static void CLHEP::RandPoissonQ::shootArray ( HepRandomEngine anEngine,
const int  size,
long *  vect,
double  mean = 1.0 
)
static

◆ showEngineStatus()

void CLHEP::HepRandom::showEngineStatus ( )
staticinherited

◆ tableBoundary()

static int CLHEP::RandPoissonQ::tableBoundary ( )
inlinestatic

Field Documentation

◆ a0

double CLHEP::RandPoissonQ::a0
private

Definition at line 127 of file RandPoissonQ.h.

Referenced by fire(), get(), put(), and setupForDefaultMu().

◆ a1

double CLHEP::RandPoissonQ::a1
private

Definition at line 128 of file RandPoissonQ.h.

Referenced by fire(), get(), put(), and setupForDefaultMu().

◆ a2

double CLHEP::RandPoissonQ::a2
private

Definition at line 129 of file RandPoissonQ.h.

Referenced by fire(), get(), put(), and setupForDefaultMu().

◆ BELOW

const int CLHEP::RandPoissonQ::BELOW = 30
staticprivate

Definition at line 145 of file RandPoissonQ.h.

Referenced by poissonDeviateSmall().

◆ defaultMean

double CLHEP::RandPoisson::defaultMean
protectedinherited

◆ ENTRIES

const int CLHEP::RandPoissonQ::ENTRIES = 51
staticprivate

Definition at line 146 of file RandPoissonQ.h.

Referenced by poissonDeviateSmall().

◆ FIRST_MU

const double CLHEP::RandPoissonQ::FIRST_MU = 10
staticprivate

Definition at line 142 of file RandPoissonQ.h.

Referenced by poissonDeviateSmall().

◆ LAST_MU

const double CLHEP::RandPoissonQ::LAST_MU = 95
staticprivate

Definition at line 143 of file RandPoissonQ.h.

Referenced by fire(), poissonDeviateSmall(), and shoot().

◆ localEngine

std::shared_ptr<HepRandomEngine> CLHEP::RandPoisson::localEngine
privateinherited

Definition at line 117 of file RandPoisson.h.

Referenced by CLHEP::RandPoisson::engine(), and CLHEP::RandPoisson::fire().

◆ MAXIMUM_POISSON_DEVIATE

const double CLHEP::RandPoissonQ::MAXIMUM_POISSON_DEVIATE = 2.0E9
static

Definition at line 108 of file RandPoissonQ.h.

Referenced by poissonDeviateQuick().

◆ meanMax

double CLHEP::RandPoisson::meanMax
protectedinherited

◆ meanMax_st

const double CLHEP::RandPoisson::meanMax_st = 2.0E9
staticprivateinherited

Definition at line 123 of file RandPoisson.h.

Referenced by CLHEP::RandPoisson::getMaxMean().

◆ oldm

double CLHEP::RandPoisson::oldm
privateinherited

◆ oldm_st

CLHEP_THREAD_LOCAL double CLHEP::RandPoisson::oldm_st = -1.0
staticprivateinherited

◆ S

const double CLHEP::RandPoissonQ::S = 5
staticprivate

Definition at line 144 of file RandPoissonQ.h.

Referenced by fire(), poissonDeviateSmall(), and shoot().

◆ seedTable

const long CLHEP::HepRandom::seedTable
staticprotectedinherited

Definition at line 156 of file Random.h.

◆ sigma

double CLHEP::RandPoissonQ::sigma
private

Definition at line 130 of file RandPoissonQ.h.

Referenced by fire(), get(), put(), and setupForDefaultMu().

◆ status

double CLHEP::RandPoisson::status[3]
privateinherited

◆ status_st

CLHEP_THREAD_LOCAL double CLHEP::RandPoisson::status_st = {0., 0., 0.}
staticprivateinherited

The documentation for this class was generated from the following files: