NEST  2.6.0,not_revisioned_source_dir@0
poisson_randomdev.h
Go to the documentation of this file.
1 /*
2  * poisson_randomdev.h
3  *
4  * This file is part of NEST.
5  *
6  * Copyright (C) 2004 The NEST Initiative
7  *
8  * NEST is free software: you can redistribute it and/or modify
9  * it under the terms of the GNU General Public License as published by
10  * the Free Software Foundation, either version 2 of the License, or
11  * (at your option) any later version.
12  *
13  * NEST is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16  * GNU General Public License for more details.
17  *
18  * You should have received a copy of the GNU General Public License
19  * along with NEST. If not, see <http://www.gnu.org/licenses/>.
20  *
21  */
22 
23 #ifndef POISSON_RANDOMDEV_H
24 #define POISSON_RANDOMDEV_H
25 
26 #include <cmath>
27 #include <vector>
28 
29 #include "randomgen.h"
30 #include "randomdev.h"
31 #include "lockptr.h"
32 
33 /************************************************************/
34 /* Class PoissonRNG */
35 /* */
36 /* Generates an RNG which returns Poisson(x; lambda) */
37 /* distributed random numbers out of an RNG which returns */
38 /* uniformly distributed random numbers: */
39 /* */
40 /* p(n) = (lambda^n / n!) exp(-lambda) , n = 0, 1, ... */
41 /* */
42 /* Arguments: */
43 /* - pointer to an RNG */
44 /* - parameters lambda (optional, default = 1) */
45 /* */
46 /* Algorithm: Ahrens & Dieter [1] */
47 /* - table lookup for lambda < 10 */
48 /* - involved rejection scheme based on normal random dev */
49 /* otherwise */
50 /* - answer to [2], Sec 3.4.1, exercise 8 */
51 /* - changing lambda involves some costly computations */
52 /* */
53 /* Verification: */
54 /* - 60 different lambda, 0.01 .. 100 */
55 /* - 10.000.000 numbers generated per lambda */
56 /* - mt19937 as uniform rng source */
57 /* - chi^2 test on batches of 10000 numbers */
58 /* - Kolmogorov-Smirnov test on chi^2 test scores */
59 /* - lambda == 0.01 critical, most likely due problems */
60 /* with test (just two bins in chi^2 test) */
61 /* - lambda == 20 failed KS test once, passed on second */
62 /* set of 10^7 numbers generated with different seed */
63 /* */
64 /* References: */
65 /* [1] J H Ahrens, U Dieter, ACM TOMS 8:163-179(1982) */
66 /* [2] D E Knuth, The Art of Computer Programming, vol 2. */
67 /* */
68 /* Author: */
69 /* Hans Ekkehard Plesser */
70 /* */
71 /* History: */
72 /* 3.0 HEP, 2003-05-23 Ahrens & Dieter algorithm */
73 /* 2.0 HEP, 2002-07-09 (for librandom 2.0) */
74 /* */
75 /* To do: */
76 /* - some of the numerics has only floating point accuracy */
77 /* should be improved to double. */
78 
79 /************************************************************/
80 
81 namespace librandom {
82 
83 /*BeginDocumentation
84 Name: rdevdict::poisson - poisson random deviate generator
85 Description:
86  Generates poisson distributed random numbers.
87 
88  p(n) = (lambda^n / n!) exp(-lambda) , n = 0, 1, ...
89 
90 Parameters:
91  lambda - distribution parameter, lambda
92 
93 SeeAlso: CreateRDV, RandomArray, rdevdict
94 Author: Hans Ekkehard Plesser
95 */
96 
104  {
105  RngPtr r; // pointer to underlying uniform RNG
106 
107  public:
108 
109 
110  // accept only lockPTRs for initialization,
111  // otherwise creation of a lock ptr would
112  // occur as side effect---might be unhealthy
113  PoissonRandomDev(RngPtr, double lambda = 0.0);
114  PoissonRandomDev(double lambda = 0.0); // for threaded environments
115 
116  void set_lambda(double);
117 
119  void set_status(const DictionaryDatum&);
120 
122  void get_status(DictionaryDatum&) const;
123 
132  using RandomDev::operator();
133  using RandomDev::ldev;
134 
135  long ldev(RngPtr) const;
136  bool has_ldev() const { return true; }
137 
138  double operator()(RngPtr) const;
139 
140  private:
141  void init_();
142 
143  double mu_;
144 
145  // quantities for case A, steps N, I, S
146  double s_;
147  double d_;
148  unsigned long L_;
149 
150  // quantities for case A, step H
151  double c_;
152 
153  // quantities for case A, function F
154  double om_;
155  double c0_;
156  double c1_;
157  double c2_;
158  double c3_;
159 
160  static const unsigned n_tab_;
161  std::vector<double> P_;
162 
163  static const unsigned fact_[];
164 
165  static const double a_[];
166  static const unsigned n_a_;
167 
169  void proc_f_(const unsigned k, double &px, double &py,
170  double &fx, double &fy) const;
171 
172  };
173 
174 }
175 
176 inline
178 {
179  return static_cast<double>(ldev(rthrd));
180 }
181 
182 # endif
static const unsigned n_a_
length of array
Definition: poisson_randomdev.h:166
virtual double operator()(void)
Operator delivering doubles.
Definition: randomdev.h:199
double c1_
Definition: poisson_randomdev.h:156
double c3_
Definition: poisson_randomdev.h:158
void set_lambda(double)
Definition: poisson_randomdev.cpp:76
double c2_
Definition: poisson_randomdev.h:157
double om_
Definition: poisson_randomdev.h:154
std::vector< double > P_
PoissonCDF.
Definition: poisson_randomdev.h:161
void set_status(const DictionaryDatum &)
set distribution parameters from SLI dict
Definition: poisson_randomdev.cpp:82
void proc_f_(const unsigned k, double &px, double &py, double &fx, double &fy) const
Procedure F from Ahrens & Dieter.
Definition: poisson_randomdev.cpp:299
static const unsigned fact_[]
array of factorials 0! .. 10!
Definition: poisson_randomdev.h:163
double mu_
Poisson parameter, aka lambda.
Definition: poisson_randomdev.h:143
Class PoissonRandomDev Create Poisson distributed random numbers.
Definition: poisson_randomdev.h:103
double s_
sqrt(mu_)
Definition: poisson_randomdev.h:146
static const double a_[]
array of a_i coeffs
Definition: poisson_randomdev.h:165
PoissonRandomDev(RngPtr, double lambda=0.0)
Definition: poisson_randomdev.cpp:63
RngPtr r
Definition: poisson_randomdev.h:105
bool has_ldev() const
true if RDG implements ldev function
Definition: poisson_randomdev.h:136
Abstract base class for access to non-uniform random deviate generators.
Definition: randomdev.h:131
virtual long ldev(void)
integer valued functions for discrete distributions
Definition: randomdev.h:206
void get_status(DictionaryDatum &) const
get distribution parameters from SLI dict
Definition: poisson_randomdev.cpp:115
unsigned long L_
floor(mu-1.1484)
Definition: poisson_randomdev.h:148
static const unsigned n_tab_
tabulate P_0 ... P_{n_tab_-1}
Definition: poisson_randomdev.h:160
double c0_
Definition: poisson_randomdev.h:155
double c_
0.1069 / mu_
Definition: poisson_randomdev.h:151
double d_
6 mu_^2
Definition: poisson_randomdev.h:147
void init_()
re-compute internal parameters
Definition: poisson_randomdev.cpp:120