1 //===----------------------------------------------------------------------===//
2 //
3 // The LLVM Compiler Infrastructure
4 //
5 // This file is dual licensed under the MIT and the University of Illinois Open
6 // Source Licenses. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // REQUIRES: long_tests
11
12 // <random>
13
14 // template<class RealType = double>
15 // class lognormal_distribution
16
17 // template<class _URNG> result_type operator()(_URNG& g);
18
19 #include <random>
20 #include <cassert>
21 #include <vector>
22 #include <numeric>
23
24 template <class T>
25 inline
26 T
sqr(T x)27 sqr(T x)
28 {
29 return x * x;
30 }
31
main()32 int main()
33 {
34 {
35 typedef std::lognormal_distribution<> D;
36 typedef D::param_type P;
37 typedef std::mt19937 G;
38 G g;
39 D d(-1./8192, 0.015625);
40 const int N = 1000000;
41 std::vector<D::result_type> u;
42 for (int i = 0; i < N; ++i)
43 {
44 D::result_type v = d(g);
45 assert(v > 0);
46 u.push_back(v);
47 }
48 double mean = std::accumulate(u.begin(), u.end(), 0.0) / u.size();
49 double var = 0;
50 double skew = 0;
51 double kurtosis = 0;
52 for (int i = 0; i < u.size(); ++i)
53 {
54 double d = (u[i] - mean);
55 double d2 = sqr(d);
56 var += d2;
57 skew += d * d2;
58 kurtosis += d2 * d2;
59 }
60 var /= u.size();
61 double dev = std::sqrt(var);
62 skew /= u.size() * dev * var;
63 kurtosis /= u.size() * var * var;
64 kurtosis -= 3;
65 double x_mean = std::exp(d.m() + sqr(d.s())/2);
66 double x_var = (std::exp(sqr(d.s())) - 1) * std::exp(2*d.m() + sqr(d.s()));
67 double x_skew = (std::exp(sqr(d.s())) + 2) *
68 std::sqrt((std::exp(sqr(d.s())) - 1));
69 double x_kurtosis = std::exp(4*sqr(d.s())) + 2*std::exp(3*sqr(d.s())) +
70 3*std::exp(2*sqr(d.s())) - 6;
71 assert(std::abs((mean - x_mean) / x_mean) < 0.01);
72 assert(std::abs((var - x_var) / x_var) < 0.01);
73 assert(std::abs((skew - x_skew) / x_skew) < 0.05);
74 assert(std::abs((kurtosis - x_kurtosis) / x_kurtosis) < 0.25);
75 }
76 {
77 typedef std::lognormal_distribution<> D;
78 typedef D::param_type P;
79 typedef std::mt19937 G;
80 G g;
81 D d(-1./32, 0.25);
82 const int N = 1000000;
83 std::vector<D::result_type> u;
84 for (int i = 0; i < N; ++i)
85 {
86 D::result_type v = d(g);
87 assert(v > 0);
88 u.push_back(v);
89 }
90 double mean = std::accumulate(u.begin(), u.end(), 0.0) / u.size();
91 double var = 0;
92 double skew = 0;
93 double kurtosis = 0;
94 for (int i = 0; i < u.size(); ++i)
95 {
96 double d = (u[i] - mean);
97 double d2 = sqr(d);
98 var += d2;
99 skew += d * d2;
100 kurtosis += d2 * d2;
101 }
102 var /= u.size();
103 double dev = std::sqrt(var);
104 skew /= u.size() * dev * var;
105 kurtosis /= u.size() * var * var;
106 kurtosis -= 3;
107 double x_mean = std::exp(d.m() + sqr(d.s())/2);
108 double x_var = (std::exp(sqr(d.s())) - 1) * std::exp(2*d.m() + sqr(d.s()));
109 double x_skew = (std::exp(sqr(d.s())) + 2) *
110 std::sqrt((std::exp(sqr(d.s())) - 1));
111 double x_kurtosis = std::exp(4*sqr(d.s())) + 2*std::exp(3*sqr(d.s())) +
112 3*std::exp(2*sqr(d.s())) - 6;
113 assert(std::abs((mean - x_mean) / x_mean) < 0.01);
114 assert(std::abs((var - x_var) / x_var) < 0.01);
115 assert(std::abs((skew - x_skew) / x_skew) < 0.01);
116 assert(std::abs((kurtosis - x_kurtosis) / x_kurtosis) < 0.03);
117 }
118 {
119 typedef std::lognormal_distribution<> D;
120 typedef D::param_type P;
121 typedef std::mt19937 G;
122 G g;
123 D d(-1./8, 0.5);
124 const int N = 1000000;
125 std::vector<D::result_type> u;
126 for (int i = 0; i < N; ++i)
127 {
128 D::result_type v = d(g);
129 assert(v > 0);
130 u.push_back(v);
131 }
132 double mean = std::accumulate(u.begin(), u.end(), 0.0) / u.size();
133 double var = 0;
134 double skew = 0;
135 double kurtosis = 0;
136 for (int i = 0; i < u.size(); ++i)
137 {
138 double d = (u[i] - mean);
139 double d2 = sqr(d);
140 var += d2;
141 skew += d * d2;
142 kurtosis += d2 * d2;
143 }
144 var /= u.size();
145 double dev = std::sqrt(var);
146 skew /= u.size() * dev * var;
147 kurtosis /= u.size() * var * var;
148 kurtosis -= 3;
149 double x_mean = std::exp(d.m() + sqr(d.s())/2);
150 double x_var = (std::exp(sqr(d.s())) - 1) * std::exp(2*d.m() + sqr(d.s()));
151 double x_skew = (std::exp(sqr(d.s())) + 2) *
152 std::sqrt((std::exp(sqr(d.s())) - 1));
153 double x_kurtosis = std::exp(4*sqr(d.s())) + 2*std::exp(3*sqr(d.s())) +
154 3*std::exp(2*sqr(d.s())) - 6;
155 assert(std::abs((mean - x_mean) / x_mean) < 0.01);
156 assert(std::abs((var - x_var) / x_var) < 0.01);
157 assert(std::abs((skew - x_skew) / x_skew) < 0.02);
158 assert(std::abs((kurtosis - x_kurtosis) / x_kurtosis) < 0.05);
159 }
160 {
161 typedef std::lognormal_distribution<> D;
162 typedef D::param_type P;
163 typedef std::mt19937 G;
164 G g;
165 D d;
166 const int N = 1000000;
167 std::vector<D::result_type> u;
168 for (int i = 0; i < N; ++i)
169 {
170 D::result_type v = d(g);
171 assert(v > 0);
172 u.push_back(v);
173 }
174 double mean = std::accumulate(u.begin(), u.end(), 0.0) / u.size();
175 double var = 0;
176 double skew = 0;
177 double kurtosis = 0;
178 for (int i = 0; i < u.size(); ++i)
179 {
180 double d = (u[i] - mean);
181 double d2 = sqr(d);
182 var += d2;
183 skew += d * d2;
184 kurtosis += d2 * d2;
185 }
186 var /= u.size();
187 double dev = std::sqrt(var);
188 skew /= u.size() * dev * var;
189 kurtosis /= u.size() * var * var;
190 kurtosis -= 3;
191 double x_mean = std::exp(d.m() + sqr(d.s())/2);
192 double x_var = (std::exp(sqr(d.s())) - 1) * std::exp(2*d.m() + sqr(d.s()));
193 double x_skew = (std::exp(sqr(d.s())) + 2) *
194 std::sqrt((std::exp(sqr(d.s())) - 1));
195 double x_kurtosis = std::exp(4*sqr(d.s())) + 2*std::exp(3*sqr(d.s())) +
196 3*std::exp(2*sqr(d.s())) - 6;
197 assert(std::abs((mean - x_mean) / x_mean) < 0.01);
198 assert(std::abs((var - x_var) / x_var) < 0.02);
199 assert(std::abs((skew - x_skew) / x_skew) < 0.08);
200 assert(std::abs((kurtosis - x_kurtosis) / x_kurtosis) < 0.4);
201 }
202 {
203 typedef std::lognormal_distribution<> D;
204 typedef D::param_type P;
205 typedef std::mt19937 G;
206 G g;
207 D d(-0.78125, 1.25);
208 const int N = 1000000;
209 std::vector<D::result_type> u;
210 for (int i = 0; i < N; ++i)
211 {
212 D::result_type v = d(g);
213 assert(v > 0);
214 u.push_back(v);
215 }
216 double mean = std::accumulate(u.begin(), u.end(), 0.0) / u.size();
217 double var = 0;
218 double skew = 0;
219 double kurtosis = 0;
220 for (int i = 0; i < u.size(); ++i)
221 {
222 double d = (u[i] - mean);
223 double d2 = sqr(d);
224 var += d2;
225 skew += d * d2;
226 kurtosis += d2 * d2;
227 }
228 var /= u.size();
229 double dev = std::sqrt(var);
230 skew /= u.size() * dev * var;
231 kurtosis /= u.size() * var * var;
232 kurtosis -= 3;
233 double x_mean = std::exp(d.m() + sqr(d.s())/2);
234 double x_var = (std::exp(sqr(d.s())) - 1) * std::exp(2*d.m() + sqr(d.s()));
235 double x_skew = (std::exp(sqr(d.s())) + 2) *
236 std::sqrt((std::exp(sqr(d.s())) - 1));
237 double x_kurtosis = std::exp(4*sqr(d.s())) + 2*std::exp(3*sqr(d.s())) +
238 3*std::exp(2*sqr(d.s())) - 6;
239 assert(std::abs((mean - x_mean) / x_mean) < 0.01);
240 assert(std::abs((var - x_var) / x_var) < 0.04);
241 assert(std::abs((skew - x_skew) / x_skew) < 0.2);
242 assert(std::abs((kurtosis - x_kurtosis) / x_kurtosis) < 0.7);
243 }
244 }
245