1 // random number generation -*- C++ -*-
2
3 // Copyright (C) 2009-2020 Free Software Foundation, Inc.
4 //
5 // This file is part of the GNU ISO C++ Library. This library is free
6 // software; you can redistribute it and/or modify it under the
7 // terms of the GNU General Public License as published by the
8 // Free Software Foundation; either version 3, or (at your option)
9 // any later version.
10
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 // GNU General Public License for more details.
15
16 // Under Section 7 of GPL version 3, you are granted additional
17 // permissions described in the GCC Runtime Library Exception, version
18 // 3.1, as published by the Free Software Foundation.
19
20 // You should have received a copy of the GNU General Public License and
21 // a copy of the GCC Runtime Library Exception along with this program;
22 // see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
23 // <http://www.gnu.org/licenses/>.
24
25 /**
26 * @file bits/random.h
27 * This is an internal header file, included by other library headers.
28 * Do not attempt to use it directly. @headername{random}
29 */
30
31 #ifndef _RANDOM_H
32 #define _RANDOM_H 1
33
34 #include <vector>
35 #include <bits/uniform_int_dist.h>
36
_GLIBCXX_VISIBILITY(default)37 namespace std _GLIBCXX_VISIBILITY(default)
38 {
39 _GLIBCXX_BEGIN_NAMESPACE_VERSION
40
41 // [26.4] Random number generation
42
43 /**
44 * @defgroup random Random Number Generation
45 * @ingroup numerics
46 *
47 * A facility for generating random numbers on selected distributions.
48 * @{
49 */
50
51 // std::uniform_random_bit_generator is defined in <bits/uniform_int_dist.h>
52
53 /**
54 * @brief A function template for converting the output of a (integral)
55 * uniform random number generator to a floatng point result in the range
56 * [0-1).
57 */
58 template<typename _RealType, size_t __bits,
59 typename _UniformRandomNumberGenerator>
60 _RealType
61 generate_canonical(_UniformRandomNumberGenerator& __g);
62
63 /*
64 * Implementation-space details.
65 */
66 namespace __detail
67 {
68 template<typename _UIntType, size_t __w,
69 bool = __w < static_cast<size_t>
70 (std::numeric_limits<_UIntType>::digits)>
71 struct _Shift
72 { static const _UIntType __value = 0; };
73
74 template<typename _UIntType, size_t __w>
75 struct _Shift<_UIntType, __w, true>
76 { static const _UIntType __value = _UIntType(1) << __w; };
77
78 template<int __s,
79 int __which = ((__s <= __CHAR_BIT__ * sizeof (int))
80 + (__s <= __CHAR_BIT__ * sizeof (long))
81 + (__s <= __CHAR_BIT__ * sizeof (long long))
82 /* assume long long no bigger than __int128 */
83 + (__s <= 128))>
84 struct _Select_uint_least_t
85 {
86 static_assert(__which < 0, /* needs to be dependent */
87 "sorry, would be too much trouble for a slow result");
88 };
89
90 template<int __s>
91 struct _Select_uint_least_t<__s, 4>
92 { typedef unsigned int type; };
93
94 template<int __s>
95 struct _Select_uint_least_t<__s, 3>
96 { typedef unsigned long type; };
97
98 template<int __s>
99 struct _Select_uint_least_t<__s, 2>
100 { typedef unsigned long long type; };
101
102 #ifdef _GLIBCXX_USE_INT128
103 template<int __s>
104 struct _Select_uint_least_t<__s, 1>
105 { typedef unsigned __int128 type; };
106 #endif
107
108 // Assume a != 0, a < m, c < m, x < m.
109 template<typename _Tp, _Tp __m, _Tp __a, _Tp __c,
110 bool __big_enough = (!(__m & (__m - 1))
111 || (_Tp(-1) - __c) / __a >= __m - 1),
112 bool __schrage_ok = __m % __a < __m / __a>
113 struct _Mod
114 {
115 typedef typename _Select_uint_least_t<std::__lg(__a)
116 + std::__lg(__m) + 2>::type _Tp2;
117 static _Tp
118 __calc(_Tp __x)
119 { return static_cast<_Tp>((_Tp2(__a) * __x + __c) % __m); }
120 };
121
122 // Schrage.
123 template<typename _Tp, _Tp __m, _Tp __a, _Tp __c>
124 struct _Mod<_Tp, __m, __a, __c, false, true>
125 {
126 static _Tp
127 __calc(_Tp __x);
128 };
129
130 // Special cases:
131 // - for m == 2^n or m == 0, unsigned integer overflow is safe.
132 // - a * (m - 1) + c fits in _Tp, there is no overflow.
133 template<typename _Tp, _Tp __m, _Tp __a, _Tp __c, bool __s>
134 struct _Mod<_Tp, __m, __a, __c, true, __s>
135 {
136 static _Tp
137 __calc(_Tp __x)
138 {
139 _Tp __res = __a * __x + __c;
140 if (__m)
141 __res %= __m;
142 return __res;
143 }
144 };
145
146 template<typename _Tp, _Tp __m, _Tp __a = 1, _Tp __c = 0>
147 inline _Tp
148 __mod(_Tp __x)
149 {
150 if _GLIBCXX17_CONSTEXPR (__a == 0)
151 return __c;
152 else
153 {
154 // _Mod must not be instantiated with a == 0
155 constexpr _Tp __a1 = __a ? __a : 1;
156 return _Mod<_Tp, __m, __a1, __c>::__calc(__x);
157 }
158 }
159
160 /*
161 * An adaptor class for converting the output of any Generator into
162 * the input for a specific Distribution.
163 */
164 template<typename _Engine, typename _DInputType>
165 struct _Adaptor
166 {
167 static_assert(std::is_floating_point<_DInputType>::value,
168 "template argument must be a floating point type");
169
170 public:
171 _Adaptor(_Engine& __g)
172 : _M_g(__g) { }
173
174 _DInputType
175 min() const
176 { return _DInputType(0); }
177
178 _DInputType
179 max() const
180 { return _DInputType(1); }
181
182 /*
183 * Converts a value generated by the adapted random number generator
184 * into a value in the input domain for the dependent random number
185 * distribution.
186 */
187 _DInputType
188 operator()()
189 {
190 return std::generate_canonical<_DInputType,
191 std::numeric_limits<_DInputType>::digits,
192 _Engine>(_M_g);
193 }
194
195 private:
196 _Engine& _M_g;
197 };
198
199 template<typename _Sseq>
200 using __seed_seq_generate_t = decltype(
201 std::declval<_Sseq&>().generate(std::declval<uint_least32_t*>(),
202 std::declval<uint_least32_t*>()));
203
204 // Detect whether _Sseq is a valid seed sequence for
205 // a random number engine _Engine with result type _Res.
206 template<typename _Sseq, typename _Engine, typename _Res,
207 typename _GenerateCheck = __seed_seq_generate_t<_Sseq>>
208 using __is_seed_seq = __and_<
209 __not_<is_same<__remove_cvref_t<_Sseq>, _Engine>>,
210 is_unsigned<typename _Sseq::result_type>,
211 __not_<is_convertible<_Sseq, _Res>>
212 >;
213
214 } // namespace __detail
215
216 /**
217 * @addtogroup random_generators Random Number Generators
218 * @ingroup random
219 *
220 * These classes define objects which provide random or pseudorandom
221 * numbers, either from a discrete or a continuous interval. The
222 * random number generator supplied as a part of this library are
223 * all uniform random number generators which provide a sequence of
224 * random number uniformly distributed over their range.
225 *
226 * A number generator is a function object with an operator() that
227 * takes zero arguments and returns a number.
228 *
229 * A compliant random number generator must satisfy the following
230 * requirements. <table border=1 cellpadding=10 cellspacing=0>
231 * <caption align=top>Random Number Generator Requirements</caption>
232 * <tr><td>To be documented.</td></tr> </table>
233 *
234 * @{
235 */
236
237 /**
238 * @brief A model of a linear congruential random number generator.
239 *
240 * A random number generator that produces pseudorandom numbers via
241 * linear function:
242 * @f[
243 * x_{i+1}\leftarrow(ax_{i} + c) \bmod m
244 * @f]
245 *
246 * The template parameter @p _UIntType must be an unsigned integral type
247 * large enough to store values up to (__m-1). If the template parameter
248 * @p __m is 0, the modulus @p __m used is
249 * std::numeric_limits<_UIntType>::max() plus 1. Otherwise, the template
250 * parameters @p __a and @p __c must be less than @p __m.
251 *
252 * The size of the state is @f$1@f$.
253 */
254 template<typename _UIntType, _UIntType __a, _UIntType __c, _UIntType __m>
255 class linear_congruential_engine
256 {
257 static_assert(std::is_unsigned<_UIntType>::value,
258 "result_type must be an unsigned integral type");
259 static_assert(__m == 0u || (__a < __m && __c < __m),
260 "template argument substituting __m out of bounds");
261
262 template<typename _Sseq>
263 using _If_seed_seq = typename enable_if<__detail::__is_seed_seq<
264 _Sseq, linear_congruential_engine, _UIntType>::value>::type;
265
266 public:
267 /** The type of the generated random value. */
268 typedef _UIntType result_type;
269
270 /** The multiplier. */
271 static constexpr result_type multiplier = __a;
272 /** An increment. */
273 static constexpr result_type increment = __c;
274 /** The modulus. */
275 static constexpr result_type modulus = __m;
276 static constexpr result_type default_seed = 1u;
277
278 /**
279 * @brief Constructs a %linear_congruential_engine random number
280 * generator engine with seed 1.
281 */
282 linear_congruential_engine() : linear_congruential_engine(default_seed)
283 { }
284
285 /**
286 * @brief Constructs a %linear_congruential_engine random number
287 * generator engine with seed @p __s. The default seed value
288 * is 1.
289 *
290 * @param __s The initial seed value.
291 */
292 explicit
293 linear_congruential_engine(result_type __s)
294 { seed(__s); }
295
296 /**
297 * @brief Constructs a %linear_congruential_engine random number
298 * generator engine seeded from the seed sequence @p __q.
299 *
300 * @param __q the seed sequence.
301 */
302 template<typename _Sseq, typename = _If_seed_seq<_Sseq>>
303 explicit
304 linear_congruential_engine(_Sseq& __q)
305 { seed(__q); }
306
307 /**
308 * @brief Reseeds the %linear_congruential_engine random number generator
309 * engine sequence to the seed @p __s.
310 *
311 * @param __s The new seed.
312 */
313 void
314 seed(result_type __s = default_seed);
315
316 /**
317 * @brief Reseeds the %linear_congruential_engine random number generator
318 * engine
319 * sequence using values from the seed sequence @p __q.
320 *
321 * @param __q the seed sequence.
322 */
323 template<typename _Sseq>
324 _If_seed_seq<_Sseq>
325 seed(_Sseq& __q);
326
327 /**
328 * @brief Gets the smallest possible value in the output range.
329 *
330 * The minimum depends on the @p __c parameter: if it is zero, the
331 * minimum generated must be > 0, otherwise 0 is allowed.
332 */
333 static constexpr result_type
334 min()
335 { return __c == 0u ? 1u : 0u; }
336
337 /**
338 * @brief Gets the largest possible value in the output range.
339 */
340 static constexpr result_type
341 max()
342 { return __m - 1u; }
343
344 /**
345 * @brief Discard a sequence of random numbers.
346 */
347 void
348 discard(unsigned long long __z)
349 {
350 for (; __z != 0ULL; --__z)
351 (*this)();
352 }
353
354 /**
355 * @brief Gets the next random number in the sequence.
356 */
357 result_type
358 operator()()
359 {
360 _M_x = __detail::__mod<_UIntType, __m, __a, __c>(_M_x);
361 return _M_x;
362 }
363
364 /**
365 * @brief Compares two linear congruential random number generator
366 * objects of the same type for equality.
367 *
368 * @param __lhs A linear congruential random number generator object.
369 * @param __rhs Another linear congruential random number generator
370 * object.
371 *
372 * @returns true if the infinite sequences of generated values
373 * would be equal, false otherwise.
374 */
375 friend bool
376 operator==(const linear_congruential_engine& __lhs,
377 const linear_congruential_engine& __rhs)
378 { return __lhs._M_x == __rhs._M_x; }
379
380 /**
381 * @brief Writes the textual representation of the state x(i) of x to
382 * @p __os.
383 *
384 * @param __os The output stream.
385 * @param __lcr A % linear_congruential_engine random number generator.
386 * @returns __os.
387 */
388 template<typename _UIntType1, _UIntType1 __a1, _UIntType1 __c1,
389 _UIntType1 __m1, typename _CharT, typename _Traits>
390 friend std::basic_ostream<_CharT, _Traits>&
391 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
392 const std::linear_congruential_engine<_UIntType1,
393 __a1, __c1, __m1>& __lcr);
394
395 /**
396 * @brief Sets the state of the engine by reading its textual
397 * representation from @p __is.
398 *
399 * The textual representation must have been previously written using
400 * an output stream whose imbued locale and whose type's template
401 * specialization arguments _CharT and _Traits were the same as those
402 * of @p __is.
403 *
404 * @param __is The input stream.
405 * @param __lcr A % linear_congruential_engine random number generator.
406 * @returns __is.
407 */
408 template<typename _UIntType1, _UIntType1 __a1, _UIntType1 __c1,
409 _UIntType1 __m1, typename _CharT, typename _Traits>
410 friend std::basic_istream<_CharT, _Traits>&
411 operator>>(std::basic_istream<_CharT, _Traits>& __is,
412 std::linear_congruential_engine<_UIntType1, __a1,
413 __c1, __m1>& __lcr);
414
415 private:
416 _UIntType _M_x;
417 };
418
419 /**
420 * @brief Compares two linear congruential random number generator
421 * objects of the same type for inequality.
422 *
423 * @param __lhs A linear congruential random number generator object.
424 * @param __rhs Another linear congruential random number generator
425 * object.
426 *
427 * @returns true if the infinite sequences of generated values
428 * would be different, false otherwise.
429 */
430 template<typename _UIntType, _UIntType __a, _UIntType __c, _UIntType __m>
431 inline bool
432 operator!=(const std::linear_congruential_engine<_UIntType, __a,
433 __c, __m>& __lhs,
434 const std::linear_congruential_engine<_UIntType, __a,
435 __c, __m>& __rhs)
436 { return !(__lhs == __rhs); }
437
438
439 /**
440 * A generalized feedback shift register discrete random number generator.
441 *
442 * This algorithm avoids multiplication and division and is designed to be
443 * friendly to a pipelined architecture. If the parameters are chosen
444 * correctly, this generator will produce numbers with a very long period and
445 * fairly good apparent entropy, although still not cryptographically strong.
446 *
447 * The best way to use this generator is with the predefined mt19937 class.
448 *
449 * This algorithm was originally invented by Makoto Matsumoto and
450 * Takuji Nishimura.
451 *
452 * @tparam __w Word size, the number of bits in each element of
453 * the state vector.
454 * @tparam __n The degree of recursion.
455 * @tparam __m The period parameter.
456 * @tparam __r The separation point bit index.
457 * @tparam __a The last row of the twist matrix.
458 * @tparam __u The first right-shift tempering matrix parameter.
459 * @tparam __d The first right-shift tempering matrix mask.
460 * @tparam __s The first left-shift tempering matrix parameter.
461 * @tparam __b The first left-shift tempering matrix mask.
462 * @tparam __t The second left-shift tempering matrix parameter.
463 * @tparam __c The second left-shift tempering matrix mask.
464 * @tparam __l The second right-shift tempering matrix parameter.
465 * @tparam __f Initialization multiplier.
466 */
467 template<typename _UIntType, size_t __w,
468 size_t __n, size_t __m, size_t __r,
469 _UIntType __a, size_t __u, _UIntType __d, size_t __s,
470 _UIntType __b, size_t __t,
471 _UIntType __c, size_t __l, _UIntType __f>
472 class mersenne_twister_engine
473 {
474 static_assert(std::is_unsigned<_UIntType>::value,
475 "result_type must be an unsigned integral type");
476 static_assert(1u <= __m && __m <= __n,
477 "template argument substituting __m out of bounds");
478 static_assert(__r <= __w, "template argument substituting "
479 "__r out of bound");
480 static_assert(__u <= __w, "template argument substituting "
481 "__u out of bound");
482 static_assert(__s <= __w, "template argument substituting "
483 "__s out of bound");
484 static_assert(__t <= __w, "template argument substituting "
485 "__t out of bound");
486 static_assert(__l <= __w, "template argument substituting "
487 "__l out of bound");
488 static_assert(__w <= std::numeric_limits<_UIntType>::digits,
489 "template argument substituting __w out of bound");
490 static_assert(__a <= (__detail::_Shift<_UIntType, __w>::__value - 1),
491 "template argument substituting __a out of bound");
492 static_assert(__b <= (__detail::_Shift<_UIntType, __w>::__value - 1),
493 "template argument substituting __b out of bound");
494 static_assert(__c <= (__detail::_Shift<_UIntType, __w>::__value - 1),
495 "template argument substituting __c out of bound");
496 static_assert(__d <= (__detail::_Shift<_UIntType, __w>::__value - 1),
497 "template argument substituting __d out of bound");
498 static_assert(__f <= (__detail::_Shift<_UIntType, __w>::__value - 1),
499 "template argument substituting __f out of bound");
500
501 template<typename _Sseq>
502 using _If_seed_seq = typename enable_if<__detail::__is_seed_seq<
503 _Sseq, mersenne_twister_engine, _UIntType>::value>::type;
504
505 public:
506 /** The type of the generated random value. */
507 typedef _UIntType result_type;
508
509 // parameter values
510 static constexpr size_t word_size = __w;
511 static constexpr size_t state_size = __n;
512 static constexpr size_t shift_size = __m;
513 static constexpr size_t mask_bits = __r;
514 static constexpr result_type xor_mask = __a;
515 static constexpr size_t tempering_u = __u;
516 static constexpr result_type tempering_d = __d;
517 static constexpr size_t tempering_s = __s;
518 static constexpr result_type tempering_b = __b;
519 static constexpr size_t tempering_t = __t;
520 static constexpr result_type tempering_c = __c;
521 static constexpr size_t tempering_l = __l;
522 static constexpr result_type initialization_multiplier = __f;
523 static constexpr result_type default_seed = 5489u;
524
525 // constructors and member functions
526
527 mersenne_twister_engine() : mersenne_twister_engine(default_seed) { }
528
529 explicit
530 mersenne_twister_engine(result_type __sd)
531 { seed(__sd); }
532
533 /**
534 * @brief Constructs a %mersenne_twister_engine random number generator
535 * engine seeded from the seed sequence @p __q.
536 *
537 * @param __q the seed sequence.
538 */
539 template<typename _Sseq, typename = _If_seed_seq<_Sseq>>
540 explicit
541 mersenne_twister_engine(_Sseq& __q)
542 { seed(__q); }
543
544 void
545 seed(result_type __sd = default_seed);
546
547 template<typename _Sseq>
548 _If_seed_seq<_Sseq>
549 seed(_Sseq& __q);
550
551 /**
552 * @brief Gets the smallest possible value in the output range.
553 */
554 static constexpr result_type
555 min()
556 { return 0; }
557
558 /**
559 * @brief Gets the largest possible value in the output range.
560 */
561 static constexpr result_type
562 max()
563 { return __detail::_Shift<_UIntType, __w>::__value - 1; }
564
565 /**
566 * @brief Discard a sequence of random numbers.
567 */
568 void
569 discard(unsigned long long __z);
570
571 result_type
572 operator()();
573
574 /**
575 * @brief Compares two % mersenne_twister_engine random number generator
576 * objects of the same type for equality.
577 *
578 * @param __lhs A % mersenne_twister_engine random number generator
579 * object.
580 * @param __rhs Another % mersenne_twister_engine random number
581 * generator object.
582 *
583 * @returns true if the infinite sequences of generated values
584 * would be equal, false otherwise.
585 */
586 friend bool
587 operator==(const mersenne_twister_engine& __lhs,
588 const mersenne_twister_engine& __rhs)
589 { return (std::equal(__lhs._M_x, __lhs._M_x + state_size, __rhs._M_x)
590 && __lhs._M_p == __rhs._M_p); }
591
592 /**
593 * @brief Inserts the current state of a % mersenne_twister_engine
594 * random number generator engine @p __x into the output stream
595 * @p __os.
596 *
597 * @param __os An output stream.
598 * @param __x A % mersenne_twister_engine random number generator
599 * engine.
600 *
601 * @returns The output stream with the state of @p __x inserted or in
602 * an error state.
603 */
604 template<typename _UIntType1,
605 size_t __w1, size_t __n1,
606 size_t __m1, size_t __r1,
607 _UIntType1 __a1, size_t __u1,
608 _UIntType1 __d1, size_t __s1,
609 _UIntType1 __b1, size_t __t1,
610 _UIntType1 __c1, size_t __l1, _UIntType1 __f1,
611 typename _CharT, typename _Traits>
612 friend std::basic_ostream<_CharT, _Traits>&
613 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
614 const std::mersenne_twister_engine<_UIntType1, __w1, __n1,
615 __m1, __r1, __a1, __u1, __d1, __s1, __b1, __t1, __c1,
616 __l1, __f1>& __x);
617
618 /**
619 * @brief Extracts the current state of a % mersenne_twister_engine
620 * random number generator engine @p __x from the input stream
621 * @p __is.
622 *
623 * @param __is An input stream.
624 * @param __x A % mersenne_twister_engine random number generator
625 * engine.
626 *
627 * @returns The input stream with the state of @p __x extracted or in
628 * an error state.
629 */
630 template<typename _UIntType1,
631 size_t __w1, size_t __n1,
632 size_t __m1, size_t __r1,
633 _UIntType1 __a1, size_t __u1,
634 _UIntType1 __d1, size_t __s1,
635 _UIntType1 __b1, size_t __t1,
636 _UIntType1 __c1, size_t __l1, _UIntType1 __f1,
637 typename _CharT, typename _Traits>
638 friend std::basic_istream<_CharT, _Traits>&
639 operator>>(std::basic_istream<_CharT, _Traits>& __is,
640 std::mersenne_twister_engine<_UIntType1, __w1, __n1, __m1,
641 __r1, __a1, __u1, __d1, __s1, __b1, __t1, __c1,
642 __l1, __f1>& __x);
643
644 private:
645 void _M_gen_rand();
646
647 _UIntType _M_x[state_size];
648 size_t _M_p;
649 };
650
651 /**
652 * @brief Compares two % mersenne_twister_engine random number generator
653 * objects of the same type for inequality.
654 *
655 * @param __lhs A % mersenne_twister_engine random number generator
656 * object.
657 * @param __rhs Another % mersenne_twister_engine random number
658 * generator object.
659 *
660 * @returns true if the infinite sequences of generated values
661 * would be different, false otherwise.
662 */
663 template<typename _UIntType, size_t __w,
664 size_t __n, size_t __m, size_t __r,
665 _UIntType __a, size_t __u, _UIntType __d, size_t __s,
666 _UIntType __b, size_t __t,
667 _UIntType __c, size_t __l, _UIntType __f>
668 inline bool
669 operator!=(const std::mersenne_twister_engine<_UIntType, __w, __n, __m,
670 __r, __a, __u, __d, __s, __b, __t, __c, __l, __f>& __lhs,
671 const std::mersenne_twister_engine<_UIntType, __w, __n, __m,
672 __r, __a, __u, __d, __s, __b, __t, __c, __l, __f>& __rhs)
673 { return !(__lhs == __rhs); }
674
675
676 /**
677 * @brief The Marsaglia-Zaman generator.
678 *
679 * This is a model of a Generalized Fibonacci discrete random number
680 * generator, sometimes referred to as the SWC generator.
681 *
682 * A discrete random number generator that produces pseudorandom
683 * numbers using:
684 * @f[
685 * x_{i}\leftarrow(x_{i - s} - x_{i - r} - carry_{i-1}) \bmod m
686 * @f]
687 *
688 * The size of the state is @f$r@f$
689 * and the maximum period of the generator is @f$(m^r - m^s - 1)@f$.
690 */
691 template<typename _UIntType, size_t __w, size_t __s, size_t __r>
692 class subtract_with_carry_engine
693 {
694 static_assert(std::is_unsigned<_UIntType>::value,
695 "result_type must be an unsigned integral type");
696 static_assert(0u < __s && __s < __r,
697 "0 < s < r");
698 static_assert(0u < __w && __w <= std::numeric_limits<_UIntType>::digits,
699 "template argument substituting __w out of bounds");
700
701 template<typename _Sseq>
702 using _If_seed_seq = typename enable_if<__detail::__is_seed_seq<
703 _Sseq, subtract_with_carry_engine, _UIntType>::value>::type;
704
705 public:
706 /** The type of the generated random value. */
707 typedef _UIntType result_type;
708
709 // parameter values
710 static constexpr size_t word_size = __w;
711 static constexpr size_t short_lag = __s;
712 static constexpr size_t long_lag = __r;
713 static constexpr result_type default_seed = 19780503u;
714
715 subtract_with_carry_engine() : subtract_with_carry_engine(default_seed)
716 { }
717
718 /**
719 * @brief Constructs an explicitly seeded %subtract_with_carry_engine
720 * random number generator.
721 */
722 explicit
723 subtract_with_carry_engine(result_type __sd)
724 { seed(__sd); }
725
726 /**
727 * @brief Constructs a %subtract_with_carry_engine random number engine
728 * seeded from the seed sequence @p __q.
729 *
730 * @param __q the seed sequence.
731 */
732 template<typename _Sseq, typename = _If_seed_seq<_Sseq>>
733 explicit
734 subtract_with_carry_engine(_Sseq& __q)
735 { seed(__q); }
736
737 /**
738 * @brief Seeds the initial state @f$x_0@f$ of the random number
739 * generator.
740 *
741 * N1688[4.19] modifies this as follows. If @p __value == 0,
742 * sets value to 19780503. In any case, with a linear
743 * congruential generator lcg(i) having parameters @f$ m_{lcg} =
744 * 2147483563, a_{lcg} = 40014, c_{lcg} = 0, and lcg(0) = value
745 * @f$, sets @f$ x_{-r} \dots x_{-1} @f$ to @f$ lcg(1) \bmod m
746 * \dots lcg(r) \bmod m @f$ respectively. If @f$ x_{-1} = 0 @f$
747 * set carry to 1, otherwise sets carry to 0.
748 */
749 void
750 seed(result_type __sd = default_seed);
751
752 /**
753 * @brief Seeds the initial state @f$x_0@f$ of the
754 * % subtract_with_carry_engine random number generator.
755 */
756 template<typename _Sseq>
757 _If_seed_seq<_Sseq>
758 seed(_Sseq& __q);
759
760 /**
761 * @brief Gets the inclusive minimum value of the range of random
762 * integers returned by this generator.
763 */
764 static constexpr result_type
765 min()
766 { return 0; }
767
768 /**
769 * @brief Gets the inclusive maximum value of the range of random
770 * integers returned by this generator.
771 */
772 static constexpr result_type
773 max()
774 { return __detail::_Shift<_UIntType, __w>::__value - 1; }
775
776 /**
777 * @brief Discard a sequence of random numbers.
778 */
779 void
780 discard(unsigned long long __z)
781 {
782 for (; __z != 0ULL; --__z)
783 (*this)();
784 }
785
786 /**
787 * @brief Gets the next random number in the sequence.
788 */
789 result_type
790 operator()();
791
792 /**
793 * @brief Compares two % subtract_with_carry_engine random number
794 * generator objects of the same type for equality.
795 *
796 * @param __lhs A % subtract_with_carry_engine random number generator
797 * object.
798 * @param __rhs Another % subtract_with_carry_engine random number
799 * generator object.
800 *
801 * @returns true if the infinite sequences of generated values
802 * would be equal, false otherwise.
803 */
804 friend bool
805 operator==(const subtract_with_carry_engine& __lhs,
806 const subtract_with_carry_engine& __rhs)
807 { return (std::equal(__lhs._M_x, __lhs._M_x + long_lag, __rhs._M_x)
808 && __lhs._M_carry == __rhs._M_carry
809 && __lhs._M_p == __rhs._M_p); }
810
811 /**
812 * @brief Inserts the current state of a % subtract_with_carry_engine
813 * random number generator engine @p __x into the output stream
814 * @p __os.
815 *
816 * @param __os An output stream.
817 * @param __x A % subtract_with_carry_engine random number generator
818 * engine.
819 *
820 * @returns The output stream with the state of @p __x inserted or in
821 * an error state.
822 */
823 template<typename _UIntType1, size_t __w1, size_t __s1, size_t __r1,
824 typename _CharT, typename _Traits>
825 friend std::basic_ostream<_CharT, _Traits>&
826 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
827 const std::subtract_with_carry_engine<_UIntType1, __w1,
828 __s1, __r1>& __x);
829
830 /**
831 * @brief Extracts the current state of a % subtract_with_carry_engine
832 * random number generator engine @p __x from the input stream
833 * @p __is.
834 *
835 * @param __is An input stream.
836 * @param __x A % subtract_with_carry_engine random number generator
837 * engine.
838 *
839 * @returns The input stream with the state of @p __x extracted or in
840 * an error state.
841 */
842 template<typename _UIntType1, size_t __w1, size_t __s1, size_t __r1,
843 typename _CharT, typename _Traits>
844 friend std::basic_istream<_CharT, _Traits>&
845 operator>>(std::basic_istream<_CharT, _Traits>& __is,
846 std::subtract_with_carry_engine<_UIntType1, __w1,
847 __s1, __r1>& __x);
848
849 private:
850 /// The state of the generator. This is a ring buffer.
851 _UIntType _M_x[long_lag];
852 _UIntType _M_carry; ///< The carry
853 size_t _M_p; ///< Current index of x(i - r).
854 };
855
856 /**
857 * @brief Compares two % subtract_with_carry_engine random number
858 * generator objects of the same type for inequality.
859 *
860 * @param __lhs A % subtract_with_carry_engine random number generator
861 * object.
862 * @param __rhs Another % subtract_with_carry_engine random number
863 * generator object.
864 *
865 * @returns true if the infinite sequences of generated values
866 * would be different, false otherwise.
867 */
868 template<typename _UIntType, size_t __w, size_t __s, size_t __r>
869 inline bool
870 operator!=(const std::subtract_with_carry_engine<_UIntType, __w,
871 __s, __r>& __lhs,
872 const std::subtract_with_carry_engine<_UIntType, __w,
873 __s, __r>& __rhs)
874 { return !(__lhs == __rhs); }
875
876
877 /**
878 * Produces random numbers from some base engine by discarding blocks of
879 * data.
880 *
881 * 0 <= @p __r <= @p __p
882 */
883 template<typename _RandomNumberEngine, size_t __p, size_t __r>
884 class discard_block_engine
885 {
886 static_assert(1 <= __r && __r <= __p,
887 "template argument substituting __r out of bounds");
888
889 public:
890 /** The type of the generated random value. */
891 typedef typename _RandomNumberEngine::result_type result_type;
892
893 template<typename _Sseq>
894 using _If_seed_seq = typename enable_if<__detail::__is_seed_seq<
895 _Sseq, discard_block_engine, result_type>::value>::type;
896
897 // parameter values
898 static constexpr size_t block_size = __p;
899 static constexpr size_t used_block = __r;
900
901 /**
902 * @brief Constructs a default %discard_block_engine engine.
903 *
904 * The underlying engine is default constructed as well.
905 */
906 discard_block_engine()
907 : _M_b(), _M_n(0) { }
908
909 /**
910 * @brief Copy constructs a %discard_block_engine engine.
911 *
912 * Copies an existing base class random number generator.
913 * @param __rng An existing (base class) engine object.
914 */
915 explicit
916 discard_block_engine(const _RandomNumberEngine& __rng)
917 : _M_b(__rng), _M_n(0) { }
918
919 /**
920 * @brief Move constructs a %discard_block_engine engine.
921 *
922 * Copies an existing base class random number generator.
923 * @param __rng An existing (base class) engine object.
924 */
925 explicit
926 discard_block_engine(_RandomNumberEngine&& __rng)
927 : _M_b(std::move(__rng)), _M_n(0) { }
928
929 /**
930 * @brief Seed constructs a %discard_block_engine engine.
931 *
932 * Constructs the underlying generator engine seeded with @p __s.
933 * @param __s A seed value for the base class engine.
934 */
935 explicit
936 discard_block_engine(result_type __s)
937 : _M_b(__s), _M_n(0) { }
938
939 /**
940 * @brief Generator construct a %discard_block_engine engine.
941 *
942 * @param __q A seed sequence.
943 */
944 template<typename _Sseq, typename = _If_seed_seq<_Sseq>>
945 explicit
946 discard_block_engine(_Sseq& __q)
947 : _M_b(__q), _M_n(0)
948 { }
949
950 /**
951 * @brief Reseeds the %discard_block_engine object with the default
952 * seed for the underlying base class generator engine.
953 */
954 void
955 seed()
956 {
957 _M_b.seed();
958 _M_n = 0;
959 }
960
961 /**
962 * @brief Reseeds the %discard_block_engine object with the default
963 * seed for the underlying base class generator engine.
964 */
965 void
966 seed(result_type __s)
967 {
968 _M_b.seed(__s);
969 _M_n = 0;
970 }
971
972 /**
973 * @brief Reseeds the %discard_block_engine object with the given seed
974 * sequence.
975 * @param __q A seed generator function.
976 */
977 template<typename _Sseq>
978 _If_seed_seq<_Sseq>
979 seed(_Sseq& __q)
980 {
981 _M_b.seed(__q);
982 _M_n = 0;
983 }
984
985 /**
986 * @brief Gets a const reference to the underlying generator engine
987 * object.
988 */
989 const _RandomNumberEngine&
990 base() const noexcept
991 { return _M_b; }
992
993 /**
994 * @brief Gets the minimum value in the generated random number range.
995 */
996 static constexpr result_type
997 min()
998 { return _RandomNumberEngine::min(); }
999
1000 /**
1001 * @brief Gets the maximum value in the generated random number range.
1002 */
1003 static constexpr result_type
1004 max()
1005 { return _RandomNumberEngine::max(); }
1006
1007 /**
1008 * @brief Discard a sequence of random numbers.
1009 */
1010 void
1011 discard(unsigned long long __z)
1012 {
1013 for (; __z != 0ULL; --__z)
1014 (*this)();
1015 }
1016
1017 /**
1018 * @brief Gets the next value in the generated random number sequence.
1019 */
1020 result_type
1021 operator()();
1022
1023 /**
1024 * @brief Compares two %discard_block_engine random number generator
1025 * objects of the same type for equality.
1026 *
1027 * @param __lhs A %discard_block_engine random number generator object.
1028 * @param __rhs Another %discard_block_engine random number generator
1029 * object.
1030 *
1031 * @returns true if the infinite sequences of generated values
1032 * would be equal, false otherwise.
1033 */
1034 friend bool
1035 operator==(const discard_block_engine& __lhs,
1036 const discard_block_engine& __rhs)
1037 { return __lhs._M_b == __rhs._M_b && __lhs._M_n == __rhs._M_n; }
1038
1039 /**
1040 * @brief Inserts the current state of a %discard_block_engine random
1041 * number generator engine @p __x into the output stream
1042 * @p __os.
1043 *
1044 * @param __os An output stream.
1045 * @param __x A %discard_block_engine random number generator engine.
1046 *
1047 * @returns The output stream with the state of @p __x inserted or in
1048 * an error state.
1049 */
1050 template<typename _RandomNumberEngine1, size_t __p1, size_t __r1,
1051 typename _CharT, typename _Traits>
1052 friend std::basic_ostream<_CharT, _Traits>&
1053 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
1054 const std::discard_block_engine<_RandomNumberEngine1,
1055 __p1, __r1>& __x);
1056
1057 /**
1058 * @brief Extracts the current state of a % subtract_with_carry_engine
1059 * random number generator engine @p __x from the input stream
1060 * @p __is.
1061 *
1062 * @param __is An input stream.
1063 * @param __x A %discard_block_engine random number generator engine.
1064 *
1065 * @returns The input stream with the state of @p __x extracted or in
1066 * an error state.
1067 */
1068 template<typename _RandomNumberEngine1, size_t __p1, size_t __r1,
1069 typename _CharT, typename _Traits>
1070 friend std::basic_istream<_CharT, _Traits>&
1071 operator>>(std::basic_istream<_CharT, _Traits>& __is,
1072 std::discard_block_engine<_RandomNumberEngine1,
1073 __p1, __r1>& __x);
1074
1075 private:
1076 _RandomNumberEngine _M_b;
1077 size_t _M_n;
1078 };
1079
1080 /**
1081 * @brief Compares two %discard_block_engine random number generator
1082 * objects of the same type for inequality.
1083 *
1084 * @param __lhs A %discard_block_engine random number generator object.
1085 * @param __rhs Another %discard_block_engine random number generator
1086 * object.
1087 *
1088 * @returns true if the infinite sequences of generated values
1089 * would be different, false otherwise.
1090 */
1091 template<typename _RandomNumberEngine, size_t __p, size_t __r>
1092 inline bool
1093 operator!=(const std::discard_block_engine<_RandomNumberEngine, __p,
1094 __r>& __lhs,
1095 const std::discard_block_engine<_RandomNumberEngine, __p,
1096 __r>& __rhs)
1097 { return !(__lhs == __rhs); }
1098
1099
1100 /**
1101 * Produces random numbers by combining random numbers from some base
1102 * engine to produce random numbers with a specifies number of bits @p __w.
1103 */
1104 template<typename _RandomNumberEngine, size_t __w, typename _UIntType>
1105 class independent_bits_engine
1106 {
1107 static_assert(std::is_unsigned<_UIntType>::value,
1108 "result_type must be an unsigned integral type");
1109 static_assert(0u < __w && __w <= std::numeric_limits<_UIntType>::digits,
1110 "template argument substituting __w out of bounds");
1111
1112 template<typename _Sseq>
1113 using _If_seed_seq = typename enable_if<__detail::__is_seed_seq<
1114 _Sseq, independent_bits_engine, _UIntType>::value>::type;
1115
1116 public:
1117 /** The type of the generated random value. */
1118 typedef _UIntType result_type;
1119
1120 /**
1121 * @brief Constructs a default %independent_bits_engine engine.
1122 *
1123 * The underlying engine is default constructed as well.
1124 */
1125 independent_bits_engine()
1126 : _M_b() { }
1127
1128 /**
1129 * @brief Copy constructs a %independent_bits_engine engine.
1130 *
1131 * Copies an existing base class random number generator.
1132 * @param __rng An existing (base class) engine object.
1133 */
1134 explicit
1135 independent_bits_engine(const _RandomNumberEngine& __rng)
1136 : _M_b(__rng) { }
1137
1138 /**
1139 * @brief Move constructs a %independent_bits_engine engine.
1140 *
1141 * Copies an existing base class random number generator.
1142 * @param __rng An existing (base class) engine object.
1143 */
1144 explicit
1145 independent_bits_engine(_RandomNumberEngine&& __rng)
1146 : _M_b(std::move(__rng)) { }
1147
1148 /**
1149 * @brief Seed constructs a %independent_bits_engine engine.
1150 *
1151 * Constructs the underlying generator engine seeded with @p __s.
1152 * @param __s A seed value for the base class engine.
1153 */
1154 explicit
1155 independent_bits_engine(result_type __s)
1156 : _M_b(__s) { }
1157
1158 /**
1159 * @brief Generator construct a %independent_bits_engine engine.
1160 *
1161 * @param __q A seed sequence.
1162 */
1163 template<typename _Sseq, typename = _If_seed_seq<_Sseq>>
1164 explicit
1165 independent_bits_engine(_Sseq& __q)
1166 : _M_b(__q)
1167 { }
1168
1169 /**
1170 * @brief Reseeds the %independent_bits_engine object with the default
1171 * seed for the underlying base class generator engine.
1172 */
1173 void
1174 seed()
1175 { _M_b.seed(); }
1176
1177 /**
1178 * @brief Reseeds the %independent_bits_engine object with the default
1179 * seed for the underlying base class generator engine.
1180 */
1181 void
1182 seed(result_type __s)
1183 { _M_b.seed(__s); }
1184
1185 /**
1186 * @brief Reseeds the %independent_bits_engine object with the given
1187 * seed sequence.
1188 * @param __q A seed generator function.
1189 */
1190 template<typename _Sseq>
1191 _If_seed_seq<_Sseq>
1192 seed(_Sseq& __q)
1193 { _M_b.seed(__q); }
1194
1195 /**
1196 * @brief Gets a const reference to the underlying generator engine
1197 * object.
1198 */
1199 const _RandomNumberEngine&
1200 base() const noexcept
1201 { return _M_b; }
1202
1203 /**
1204 * @brief Gets the minimum value in the generated random number range.
1205 */
1206 static constexpr result_type
1207 min()
1208 { return 0U; }
1209
1210 /**
1211 * @brief Gets the maximum value in the generated random number range.
1212 */
1213 static constexpr result_type
1214 max()
1215 { return __detail::_Shift<_UIntType, __w>::__value - 1; }
1216
1217 /**
1218 * @brief Discard a sequence of random numbers.
1219 */
1220 void
1221 discard(unsigned long long __z)
1222 {
1223 for (; __z != 0ULL; --__z)
1224 (*this)();
1225 }
1226
1227 /**
1228 * @brief Gets the next value in the generated random number sequence.
1229 */
1230 result_type
1231 operator()();
1232
1233 /**
1234 * @brief Compares two %independent_bits_engine random number generator
1235 * objects of the same type for equality.
1236 *
1237 * @param __lhs A %independent_bits_engine random number generator
1238 * object.
1239 * @param __rhs Another %independent_bits_engine random number generator
1240 * object.
1241 *
1242 * @returns true if the infinite sequences of generated values
1243 * would be equal, false otherwise.
1244 */
1245 friend bool
1246 operator==(const independent_bits_engine& __lhs,
1247 const independent_bits_engine& __rhs)
1248 { return __lhs._M_b == __rhs._M_b; }
1249
1250 /**
1251 * @brief Extracts the current state of a % subtract_with_carry_engine
1252 * random number generator engine @p __x from the input stream
1253 * @p __is.
1254 *
1255 * @param __is An input stream.
1256 * @param __x A %independent_bits_engine random number generator
1257 * engine.
1258 *
1259 * @returns The input stream with the state of @p __x extracted or in
1260 * an error state.
1261 */
1262 template<typename _CharT, typename _Traits>
1263 friend std::basic_istream<_CharT, _Traits>&
1264 operator>>(std::basic_istream<_CharT, _Traits>& __is,
1265 std::independent_bits_engine<_RandomNumberEngine,
1266 __w, _UIntType>& __x)
1267 {
1268 __is >> __x._M_b;
1269 return __is;
1270 }
1271
1272 private:
1273 _RandomNumberEngine _M_b;
1274 };
1275
1276 /**
1277 * @brief Compares two %independent_bits_engine random number generator
1278 * objects of the same type for inequality.
1279 *
1280 * @param __lhs A %independent_bits_engine random number generator
1281 * object.
1282 * @param __rhs Another %independent_bits_engine random number generator
1283 * object.
1284 *
1285 * @returns true if the infinite sequences of generated values
1286 * would be different, false otherwise.
1287 */
1288 template<typename _RandomNumberEngine, size_t __w, typename _UIntType>
1289 inline bool
1290 operator!=(const std::independent_bits_engine<_RandomNumberEngine, __w,
1291 _UIntType>& __lhs,
1292 const std::independent_bits_engine<_RandomNumberEngine, __w,
1293 _UIntType>& __rhs)
1294 { return !(__lhs == __rhs); }
1295
1296 /**
1297 * @brief Inserts the current state of a %independent_bits_engine random
1298 * number generator engine @p __x into the output stream @p __os.
1299 *
1300 * @param __os An output stream.
1301 * @param __x A %independent_bits_engine random number generator engine.
1302 *
1303 * @returns The output stream with the state of @p __x inserted or in
1304 * an error state.
1305 */
1306 template<typename _RandomNumberEngine, size_t __w, typename _UIntType,
1307 typename _CharT, typename _Traits>
1308 std::basic_ostream<_CharT, _Traits>&
1309 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
1310 const std::independent_bits_engine<_RandomNumberEngine,
1311 __w, _UIntType>& __x)
1312 {
1313 __os << __x.base();
1314 return __os;
1315 }
1316
1317
1318 /**
1319 * @brief Produces random numbers by combining random numbers from some
1320 * base engine to produce random numbers with a specifies number of bits
1321 * @p __k.
1322 */
1323 template<typename _RandomNumberEngine, size_t __k>
1324 class shuffle_order_engine
1325 {
1326 static_assert(1u <= __k, "template argument substituting "
1327 "__k out of bound");
1328
1329 public:
1330 /** The type of the generated random value. */
1331 typedef typename _RandomNumberEngine::result_type result_type;
1332
1333 template<typename _Sseq>
1334 using _If_seed_seq = typename enable_if<__detail::__is_seed_seq<
1335 _Sseq, shuffle_order_engine, result_type>::value>::type;
1336
1337 static constexpr size_t table_size = __k;
1338
1339 /**
1340 * @brief Constructs a default %shuffle_order_engine engine.
1341 *
1342 * The underlying engine is default constructed as well.
1343 */
1344 shuffle_order_engine()
1345 : _M_b()
1346 { _M_initialize(); }
1347
1348 /**
1349 * @brief Copy constructs a %shuffle_order_engine engine.
1350 *
1351 * Copies an existing base class random number generator.
1352 * @param __rng An existing (base class) engine object.
1353 */
1354 explicit
1355 shuffle_order_engine(const _RandomNumberEngine& __rng)
1356 : _M_b(__rng)
1357 { _M_initialize(); }
1358
1359 /**
1360 * @brief Move constructs a %shuffle_order_engine engine.
1361 *
1362 * Copies an existing base class random number generator.
1363 * @param __rng An existing (base class) engine object.
1364 */
1365 explicit
1366 shuffle_order_engine(_RandomNumberEngine&& __rng)
1367 : _M_b(std::move(__rng))
1368 { _M_initialize(); }
1369
1370 /**
1371 * @brief Seed constructs a %shuffle_order_engine engine.
1372 *
1373 * Constructs the underlying generator engine seeded with @p __s.
1374 * @param __s A seed value for the base class engine.
1375 */
1376 explicit
1377 shuffle_order_engine(result_type __s)
1378 : _M_b(__s)
1379 { _M_initialize(); }
1380
1381 /**
1382 * @brief Generator construct a %shuffle_order_engine engine.
1383 *
1384 * @param __q A seed sequence.
1385 */
1386 template<typename _Sseq, typename = _If_seed_seq<_Sseq>>
1387 explicit
1388 shuffle_order_engine(_Sseq& __q)
1389 : _M_b(__q)
1390 { _M_initialize(); }
1391
1392 /**
1393 * @brief Reseeds the %shuffle_order_engine object with the default seed
1394 for the underlying base class generator engine.
1395 */
1396 void
1397 seed()
1398 {
1399 _M_b.seed();
1400 _M_initialize();
1401 }
1402
1403 /**
1404 * @brief Reseeds the %shuffle_order_engine object with the default seed
1405 * for the underlying base class generator engine.
1406 */
1407 void
1408 seed(result_type __s)
1409 {
1410 _M_b.seed(__s);
1411 _M_initialize();
1412 }
1413
1414 /**
1415 * @brief Reseeds the %shuffle_order_engine object with the given seed
1416 * sequence.
1417 * @param __q A seed generator function.
1418 */
1419 template<typename _Sseq>
1420 _If_seed_seq<_Sseq>
1421 seed(_Sseq& __q)
1422 {
1423 _M_b.seed(__q);
1424 _M_initialize();
1425 }
1426
1427 /**
1428 * Gets a const reference to the underlying generator engine object.
1429 */
1430 const _RandomNumberEngine&
1431 base() const noexcept
1432 { return _M_b; }
1433
1434 /**
1435 * Gets the minimum value in the generated random number range.
1436 */
1437 static constexpr result_type
1438 min()
1439 { return _RandomNumberEngine::min(); }
1440
1441 /**
1442 * Gets the maximum value in the generated random number range.
1443 */
1444 static constexpr result_type
1445 max()
1446 { return _RandomNumberEngine::max(); }
1447
1448 /**
1449 * Discard a sequence of random numbers.
1450 */
1451 void
1452 discard(unsigned long long __z)
1453 {
1454 for (; __z != 0ULL; --__z)
1455 (*this)();
1456 }
1457
1458 /**
1459 * Gets the next value in the generated random number sequence.
1460 */
1461 result_type
1462 operator()();
1463
1464 /**
1465 * Compares two %shuffle_order_engine random number generator objects
1466 * of the same type for equality.
1467 *
1468 * @param __lhs A %shuffle_order_engine random number generator object.
1469 * @param __rhs Another %shuffle_order_engine random number generator
1470 * object.
1471 *
1472 * @returns true if the infinite sequences of generated values
1473 * would be equal, false otherwise.
1474 */
1475 friend bool
1476 operator==(const shuffle_order_engine& __lhs,
1477 const shuffle_order_engine& __rhs)
1478 { return (__lhs._M_b == __rhs._M_b
1479 && std::equal(__lhs._M_v, __lhs._M_v + __k, __rhs._M_v)
1480 && __lhs._M_y == __rhs._M_y); }
1481
1482 /**
1483 * @brief Inserts the current state of a %shuffle_order_engine random
1484 * number generator engine @p __x into the output stream
1485 @p __os.
1486 *
1487 * @param __os An output stream.
1488 * @param __x A %shuffle_order_engine random number generator engine.
1489 *
1490 * @returns The output stream with the state of @p __x inserted or in
1491 * an error state.
1492 */
1493 template<typename _RandomNumberEngine1, size_t __k1,
1494 typename _CharT, typename _Traits>
1495 friend std::basic_ostream<_CharT, _Traits>&
1496 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
1497 const std::shuffle_order_engine<_RandomNumberEngine1,
1498 __k1>& __x);
1499
1500 /**
1501 * @brief Extracts the current state of a % subtract_with_carry_engine
1502 * random number generator engine @p __x from the input stream
1503 * @p __is.
1504 *
1505 * @param __is An input stream.
1506 * @param __x A %shuffle_order_engine random number generator engine.
1507 *
1508 * @returns The input stream with the state of @p __x extracted or in
1509 * an error state.
1510 */
1511 template<typename _RandomNumberEngine1, size_t __k1,
1512 typename _CharT, typename _Traits>
1513 friend std::basic_istream<_CharT, _Traits>&
1514 operator>>(std::basic_istream<_CharT, _Traits>& __is,
1515 std::shuffle_order_engine<_RandomNumberEngine1, __k1>& __x);
1516
1517 private:
1518 void _M_initialize()
1519 {
1520 for (size_t __i = 0; __i < __k; ++__i)
1521 _M_v[__i] = _M_b();
1522 _M_y = _M_b();
1523 }
1524
1525 _RandomNumberEngine _M_b;
1526 result_type _M_v[__k];
1527 result_type _M_y;
1528 };
1529
1530 /**
1531 * Compares two %shuffle_order_engine random number generator objects
1532 * of the same type for inequality.
1533 *
1534 * @param __lhs A %shuffle_order_engine random number generator object.
1535 * @param __rhs Another %shuffle_order_engine random number generator
1536 * object.
1537 *
1538 * @returns true if the infinite sequences of generated values
1539 * would be different, false otherwise.
1540 */
1541 template<typename _RandomNumberEngine, size_t __k>
1542 inline bool
1543 operator!=(const std::shuffle_order_engine<_RandomNumberEngine,
1544 __k>& __lhs,
1545 const std::shuffle_order_engine<_RandomNumberEngine,
1546 __k>& __rhs)
1547 { return !(__lhs == __rhs); }
1548
1549
1550 /**
1551 * The classic Minimum Standard rand0 of Lewis, Goodman, and Miller.
1552 */
1553 typedef linear_congruential_engine<uint_fast32_t, 16807UL, 0UL, 2147483647UL>
1554 minstd_rand0;
1555
1556 /**
1557 * An alternative LCR (Lehmer Generator function).
1558 */
1559 typedef linear_congruential_engine<uint_fast32_t, 48271UL, 0UL, 2147483647UL>
1560 minstd_rand;
1561
1562 /**
1563 * The classic Mersenne Twister.
1564 *
1565 * Reference:
1566 * M. Matsumoto and T. Nishimura, Mersenne Twister: A 623-Dimensionally
1567 * Equidistributed Uniform Pseudo-Random Number Generator, ACM Transactions
1568 * on Modeling and Computer Simulation, Vol. 8, No. 1, January 1998, pp 3-30.
1569 */
1570 typedef mersenne_twister_engine<
1571 uint_fast32_t,
1572 32, 624, 397, 31,
1573 0x9908b0dfUL, 11,
1574 0xffffffffUL, 7,
1575 0x9d2c5680UL, 15,
1576 0xefc60000UL, 18, 1812433253UL> mt19937;
1577
1578 /**
1579 * An alternative Mersenne Twister.
1580 */
1581 typedef mersenne_twister_engine<
1582 uint_fast64_t,
1583 64, 312, 156, 31,
1584 0xb5026f5aa96619e9ULL, 29,
1585 0x5555555555555555ULL, 17,
1586 0x71d67fffeda60000ULL, 37,
1587 0xfff7eee000000000ULL, 43,
1588 6364136223846793005ULL> mt19937_64;
1589
1590 typedef subtract_with_carry_engine<uint_fast32_t, 24, 10, 24>
1591 ranlux24_base;
1592
1593 typedef subtract_with_carry_engine<uint_fast64_t, 48, 5, 12>
1594 ranlux48_base;
1595
1596 typedef discard_block_engine<ranlux24_base, 223, 23> ranlux24;
1597
1598 typedef discard_block_engine<ranlux48_base, 389, 11> ranlux48;
1599
1600 typedef shuffle_order_engine<minstd_rand0, 256> knuth_b;
1601
1602 typedef minstd_rand0 default_random_engine;
1603
1604 /**
1605 * A standard interface to a platform-specific non-deterministic
1606 * random number generator (if any are available).
1607 */
1608 class random_device
1609 {
1610 public:
1611 /** The type of the generated random value. */
1612 typedef unsigned int result_type;
1613
1614 // constructors, destructors and member functions
1615
1616 random_device() { _M_init("default"); }
1617
1618 explicit
1619 random_device(const std::string& __token) { _M_init(__token); }
1620
1621 #if defined _GLIBCXX_USE_DEV_RANDOM
1622 ~random_device()
1623 { _M_fini(); }
1624 #endif
1625
1626 static constexpr result_type
1627 min()
1628 { return std::numeric_limits<result_type>::min(); }
1629
1630 static constexpr result_type
1631 max()
1632 { return std::numeric_limits<result_type>::max(); }
1633
1634 double
1635 entropy() const noexcept
1636 {
1637 #ifdef _GLIBCXX_USE_DEV_RANDOM
1638 return this->_M_getentropy();
1639 #else
1640 return 0.0;
1641 #endif
1642 }
1643
1644 result_type
1645 operator()()
1646 { return this->_M_getval(); }
1647
1648 // No copy functions.
1649 random_device(const random_device&) = delete;
1650 void operator=(const random_device&) = delete;
1651
1652 private:
1653
1654 void _M_init(const std::string& __token);
1655 void _M_init_pretr1(const std::string& __token);
1656 void _M_fini();
1657
1658 result_type _M_getval();
1659 result_type _M_getval_pretr1();
1660 double _M_getentropy() const noexcept;
1661
1662 void _M_init(const char*, size_t); // not exported from the shared library
1663
1664 union
1665 {
1666 struct
1667 {
1668 void* _M_file;
1669 result_type (*_M_func)(void*);
1670 int _M_fd;
1671 };
1672 mt19937 _M_mt;
1673 };
1674 };
1675
1676 /* @} */ // group random_generators
1677
1678 /**
1679 * @addtogroup random_distributions Random Number Distributions
1680 * @ingroup random
1681 * @{
1682 */
1683
1684 /**
1685 * @addtogroup random_distributions_uniform Uniform Distributions
1686 * @ingroup random_distributions
1687 * @{
1688 */
1689
1690 // std::uniform_int_distribution is defined in <bits/uniform_int_dist.h>
1691
1692 /**
1693 * @brief Return true if two uniform integer distributions have
1694 * different parameters.
1695 */
1696 template<typename _IntType>
1697 inline bool
1698 operator!=(const std::uniform_int_distribution<_IntType>& __d1,
1699 const std::uniform_int_distribution<_IntType>& __d2)
1700 { return !(__d1 == __d2); }
1701
1702 /**
1703 * @brief Inserts a %uniform_int_distribution random number
1704 * distribution @p __x into the output stream @p os.
1705 *
1706 * @param __os An output stream.
1707 * @param __x A %uniform_int_distribution random number distribution.
1708 *
1709 * @returns The output stream with the state of @p __x inserted or in
1710 * an error state.
1711 */
1712 template<typename _IntType, typename _CharT, typename _Traits>
1713 std::basic_ostream<_CharT, _Traits>&
1714 operator<<(std::basic_ostream<_CharT, _Traits>&,
1715 const std::uniform_int_distribution<_IntType>&);
1716
1717 /**
1718 * @brief Extracts a %uniform_int_distribution random number distribution
1719 * @p __x from the input stream @p __is.
1720 *
1721 * @param __is An input stream.
1722 * @param __x A %uniform_int_distribution random number generator engine.
1723 *
1724 * @returns The input stream with @p __x extracted or in an error state.
1725 */
1726 template<typename _IntType, typename _CharT, typename _Traits>
1727 std::basic_istream<_CharT, _Traits>&
1728 operator>>(std::basic_istream<_CharT, _Traits>&,
1729 std::uniform_int_distribution<_IntType>&);
1730
1731
1732 /**
1733 * @brief Uniform continuous distribution for random numbers.
1734 *
1735 * A continuous random distribution on the range [min, max) with equal
1736 * probability throughout the range. The URNG should be real-valued and
1737 * deliver number in the range [0, 1).
1738 */
1739 template<typename _RealType = double>
1740 class uniform_real_distribution
1741 {
1742 static_assert(std::is_floating_point<_RealType>::value,
1743 "result_type must be a floating point type");
1744
1745 public:
1746 /** The type of the range of the distribution. */
1747 typedef _RealType result_type;
1748
1749 /** Parameter type. */
1750 struct param_type
1751 {
1752 typedef uniform_real_distribution<_RealType> distribution_type;
1753
1754 param_type() : param_type(0) { }
1755
1756 explicit
1757 param_type(_RealType __a, _RealType __b = _RealType(1))
1758 : _M_a(__a), _M_b(__b)
1759 {
1760 __glibcxx_assert(_M_a <= _M_b);
1761 }
1762
1763 result_type
1764 a() const
1765 { return _M_a; }
1766
1767 result_type
1768 b() const
1769 { return _M_b; }
1770
1771 friend bool
1772 operator==(const param_type& __p1, const param_type& __p2)
1773 { return __p1._M_a == __p2._M_a && __p1._M_b == __p2._M_b; }
1774
1775 friend bool
1776 operator!=(const param_type& __p1, const param_type& __p2)
1777 { return !(__p1 == __p2); }
1778
1779 private:
1780 _RealType _M_a;
1781 _RealType _M_b;
1782 };
1783
1784 public:
1785 /**
1786 * @brief Constructs a uniform_real_distribution object.
1787 *
1788 * The lower bound is set to 0.0 and the upper bound to 1.0
1789 */
1790 uniform_real_distribution() : uniform_real_distribution(0.0) { }
1791
1792 /**
1793 * @brief Constructs a uniform_real_distribution object.
1794 *
1795 * @param __a [IN] The lower bound of the distribution.
1796 * @param __b [IN] The upper bound of the distribution.
1797 */
1798 explicit
1799 uniform_real_distribution(_RealType __a, _RealType __b = _RealType(1))
1800 : _M_param(__a, __b)
1801 { }
1802
1803 explicit
1804 uniform_real_distribution(const param_type& __p)
1805 : _M_param(__p)
1806 { }
1807
1808 /**
1809 * @brief Resets the distribution state.
1810 *
1811 * Does nothing for the uniform real distribution.
1812 */
1813 void
1814 reset() { }
1815
1816 result_type
1817 a() const
1818 { return _M_param.a(); }
1819
1820 result_type
1821 b() const
1822 { return _M_param.b(); }
1823
1824 /**
1825 * @brief Returns the parameter set of the distribution.
1826 */
1827 param_type
1828 param() const
1829 { return _M_param; }
1830
1831 /**
1832 * @brief Sets the parameter set of the distribution.
1833 * @param __param The new parameter set of the distribution.
1834 */
1835 void
1836 param(const param_type& __param)
1837 { _M_param = __param; }
1838
1839 /**
1840 * @brief Returns the inclusive lower bound of the distribution range.
1841 */
1842 result_type
1843 min() const
1844 { return this->a(); }
1845
1846 /**
1847 * @brief Returns the inclusive upper bound of the distribution range.
1848 */
1849 result_type
1850 max() const
1851 { return this->b(); }
1852
1853 /**
1854 * @brief Generating functions.
1855 */
1856 template<typename _UniformRandomNumberGenerator>
1857 result_type
1858 operator()(_UniformRandomNumberGenerator& __urng)
1859 { return this->operator()(__urng, _M_param); }
1860
1861 template<typename _UniformRandomNumberGenerator>
1862 result_type
1863 operator()(_UniformRandomNumberGenerator& __urng,
1864 const param_type& __p)
1865 {
1866 __detail::_Adaptor<_UniformRandomNumberGenerator, result_type>
1867 __aurng(__urng);
1868 return (__aurng() * (__p.b() - __p.a())) + __p.a();
1869 }
1870
1871 template<typename _ForwardIterator,
1872 typename _UniformRandomNumberGenerator>
1873 void
1874 __generate(_ForwardIterator __f, _ForwardIterator __t,
1875 _UniformRandomNumberGenerator& __urng)
1876 { this->__generate(__f, __t, __urng, _M_param); }
1877
1878 template<typename _ForwardIterator,
1879 typename _UniformRandomNumberGenerator>
1880 void
1881 __generate(_ForwardIterator __f, _ForwardIterator __t,
1882 _UniformRandomNumberGenerator& __urng,
1883 const param_type& __p)
1884 { this->__generate_impl(__f, __t, __urng, __p); }
1885
1886 template<typename _UniformRandomNumberGenerator>
1887 void
1888 __generate(result_type* __f, result_type* __t,
1889 _UniformRandomNumberGenerator& __urng,
1890 const param_type& __p)
1891 { this->__generate_impl(__f, __t, __urng, __p); }
1892
1893 /**
1894 * @brief Return true if two uniform real distributions have
1895 * the same parameters.
1896 */
1897 friend bool
1898 operator==(const uniform_real_distribution& __d1,
1899 const uniform_real_distribution& __d2)
1900 { return __d1._M_param == __d2._M_param; }
1901
1902 private:
1903 template<typename _ForwardIterator,
1904 typename _UniformRandomNumberGenerator>
1905 void
1906 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
1907 _UniformRandomNumberGenerator& __urng,
1908 const param_type& __p);
1909
1910 param_type _M_param;
1911 };
1912
1913 /**
1914 * @brief Return true if two uniform real distributions have
1915 * different parameters.
1916 */
1917 template<typename _IntType>
1918 inline bool
1919 operator!=(const std::uniform_real_distribution<_IntType>& __d1,
1920 const std::uniform_real_distribution<_IntType>& __d2)
1921 { return !(__d1 == __d2); }
1922
1923 /**
1924 * @brief Inserts a %uniform_real_distribution random number
1925 * distribution @p __x into the output stream @p __os.
1926 *
1927 * @param __os An output stream.
1928 * @param __x A %uniform_real_distribution random number distribution.
1929 *
1930 * @returns The output stream with the state of @p __x inserted or in
1931 * an error state.
1932 */
1933 template<typename _RealType, typename _CharT, typename _Traits>
1934 std::basic_ostream<_CharT, _Traits>&
1935 operator<<(std::basic_ostream<_CharT, _Traits>&,
1936 const std::uniform_real_distribution<_RealType>&);
1937
1938 /**
1939 * @brief Extracts a %uniform_real_distribution random number distribution
1940 * @p __x from the input stream @p __is.
1941 *
1942 * @param __is An input stream.
1943 * @param __x A %uniform_real_distribution random number generator engine.
1944 *
1945 * @returns The input stream with @p __x extracted or in an error state.
1946 */
1947 template<typename _RealType, typename _CharT, typename _Traits>
1948 std::basic_istream<_CharT, _Traits>&
1949 operator>>(std::basic_istream<_CharT, _Traits>&,
1950 std::uniform_real_distribution<_RealType>&);
1951
1952 /* @} */ // group random_distributions_uniform
1953
1954 /**
1955 * @addtogroup random_distributions_normal Normal Distributions
1956 * @ingroup random_distributions
1957 * @{
1958 */
1959
1960 /**
1961 * @brief A normal continuous distribution for random numbers.
1962 *
1963 * The formula for the normal probability density function is
1964 * @f[
1965 * p(x|\mu,\sigma) = \frac{1}{\sigma \sqrt{2 \pi}}
1966 * e^{- \frac{{x - \mu}^ {2}}{2 \sigma ^ {2}} }
1967 * @f]
1968 */
1969 template<typename _RealType = double>
1970 class normal_distribution
1971 {
1972 static_assert(std::is_floating_point<_RealType>::value,
1973 "result_type must be a floating point type");
1974
1975 public:
1976 /** The type of the range of the distribution. */
1977 typedef _RealType result_type;
1978
1979 /** Parameter type. */
1980 struct param_type
1981 {
1982 typedef normal_distribution<_RealType> distribution_type;
1983
1984 param_type() : param_type(0.0) { }
1985
1986 explicit
1987 param_type(_RealType __mean, _RealType __stddev = _RealType(1))
1988 : _M_mean(__mean), _M_stddev(__stddev)
1989 {
1990 __glibcxx_assert(_M_stddev > _RealType(0));
1991 }
1992
1993 _RealType
1994 mean() const
1995 { return _M_mean; }
1996
1997 _RealType
1998 stddev() const
1999 { return _M_stddev; }
2000
2001 friend bool
2002 operator==(const param_type& __p1, const param_type& __p2)
2003 { return (__p1._M_mean == __p2._M_mean
2004 && __p1._M_stddev == __p2._M_stddev); }
2005
2006 friend bool
2007 operator!=(const param_type& __p1, const param_type& __p2)
2008 { return !(__p1 == __p2); }
2009
2010 private:
2011 _RealType _M_mean;
2012 _RealType _M_stddev;
2013 };
2014
2015 public:
2016 normal_distribution() : normal_distribution(0.0) { }
2017
2018 /**
2019 * Constructs a normal distribution with parameters @f$mean@f$ and
2020 * standard deviation.
2021 */
2022 explicit
2023 normal_distribution(result_type __mean,
2024 result_type __stddev = result_type(1))
2025 : _M_param(__mean, __stddev)
2026 { }
2027
2028 explicit
2029 normal_distribution(const param_type& __p)
2030 : _M_param(__p)
2031 { }
2032
2033 /**
2034 * @brief Resets the distribution state.
2035 */
2036 void
2037 reset()
2038 { _M_saved_available = false; }
2039
2040 /**
2041 * @brief Returns the mean of the distribution.
2042 */
2043 _RealType
2044 mean() const
2045 { return _M_param.mean(); }
2046
2047 /**
2048 * @brief Returns the standard deviation of the distribution.
2049 */
2050 _RealType
2051 stddev() const
2052 { return _M_param.stddev(); }
2053
2054 /**
2055 * @brief Returns the parameter set of the distribution.
2056 */
2057 param_type
2058 param() const
2059 { return _M_param; }
2060
2061 /**
2062 * @brief Sets the parameter set of the distribution.
2063 * @param __param The new parameter set of the distribution.
2064 */
2065 void
2066 param(const param_type& __param)
2067 { _M_param = __param; }
2068
2069 /**
2070 * @brief Returns the greatest lower bound value of the distribution.
2071 */
2072 result_type
2073 min() const
2074 { return std::numeric_limits<result_type>::lowest(); }
2075
2076 /**
2077 * @brief Returns the least upper bound value of the distribution.
2078 */
2079 result_type
2080 max() const
2081 { return std::numeric_limits<result_type>::max(); }
2082
2083 /**
2084 * @brief Generating functions.
2085 */
2086 template<typename _UniformRandomNumberGenerator>
2087 result_type
2088 operator()(_UniformRandomNumberGenerator& __urng)
2089 { return this->operator()(__urng, _M_param); }
2090
2091 template<typename _UniformRandomNumberGenerator>
2092 result_type
2093 operator()(_UniformRandomNumberGenerator& __urng,
2094 const param_type& __p);
2095
2096 template<typename _ForwardIterator,
2097 typename _UniformRandomNumberGenerator>
2098 void
2099 __generate(_ForwardIterator __f, _ForwardIterator __t,
2100 _UniformRandomNumberGenerator& __urng)
2101 { this->__generate(__f, __t, __urng, _M_param); }
2102
2103 template<typename _ForwardIterator,
2104 typename _UniformRandomNumberGenerator>
2105 void
2106 __generate(_ForwardIterator __f, _ForwardIterator __t,
2107 _UniformRandomNumberGenerator& __urng,
2108 const param_type& __p)
2109 { this->__generate_impl(__f, __t, __urng, __p); }
2110
2111 template<typename _UniformRandomNumberGenerator>
2112 void
2113 __generate(result_type* __f, result_type* __t,
2114 _UniformRandomNumberGenerator& __urng,
2115 const param_type& __p)
2116 { this->__generate_impl(__f, __t, __urng, __p); }
2117
2118 /**
2119 * @brief Return true if two normal distributions have
2120 * the same parameters and the sequences that would
2121 * be generated are equal.
2122 */
2123 template<typename _RealType1>
2124 friend bool
2125 operator==(const std::normal_distribution<_RealType1>& __d1,
2126 const std::normal_distribution<_RealType1>& __d2);
2127
2128 /**
2129 * @brief Inserts a %normal_distribution random number distribution
2130 * @p __x into the output stream @p __os.
2131 *
2132 * @param __os An output stream.
2133 * @param __x A %normal_distribution random number distribution.
2134 *
2135 * @returns The output stream with the state of @p __x inserted or in
2136 * an error state.
2137 */
2138 template<typename _RealType1, typename _CharT, typename _Traits>
2139 friend std::basic_ostream<_CharT, _Traits>&
2140 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
2141 const std::normal_distribution<_RealType1>& __x);
2142
2143 /**
2144 * @brief Extracts a %normal_distribution random number distribution
2145 * @p __x from the input stream @p __is.
2146 *
2147 * @param __is An input stream.
2148 * @param __x A %normal_distribution random number generator engine.
2149 *
2150 * @returns The input stream with @p __x extracted or in an error
2151 * state.
2152 */
2153 template<typename _RealType1, typename _CharT, typename _Traits>
2154 friend std::basic_istream<_CharT, _Traits>&
2155 operator>>(std::basic_istream<_CharT, _Traits>& __is,
2156 std::normal_distribution<_RealType1>& __x);
2157
2158 private:
2159 template<typename _ForwardIterator,
2160 typename _UniformRandomNumberGenerator>
2161 void
2162 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
2163 _UniformRandomNumberGenerator& __urng,
2164 const param_type& __p);
2165
2166 param_type _M_param;
2167 result_type _M_saved = 0;
2168 bool _M_saved_available = false;
2169 };
2170
2171 /**
2172 * @brief Return true if two normal distributions are different.
2173 */
2174 template<typename _RealType>
2175 inline bool
2176 operator!=(const std::normal_distribution<_RealType>& __d1,
2177 const std::normal_distribution<_RealType>& __d2)
2178 { return !(__d1 == __d2); }
2179
2180
2181 /**
2182 * @brief A lognormal_distribution random number distribution.
2183 *
2184 * The formula for the normal probability mass function is
2185 * @f[
2186 * p(x|m,s) = \frac{1}{sx\sqrt{2\pi}}
2187 * \exp{-\frac{(\ln{x} - m)^2}{2s^2}}
2188 * @f]
2189 */
2190 template<typename _RealType = double>
2191 class lognormal_distribution
2192 {
2193 static_assert(std::is_floating_point<_RealType>::value,
2194 "result_type must be a floating point type");
2195
2196 public:
2197 /** The type of the range of the distribution. */
2198 typedef _RealType result_type;
2199
2200 /** Parameter type. */
2201 struct param_type
2202 {
2203 typedef lognormal_distribution<_RealType> distribution_type;
2204
2205 param_type() : param_type(0.0) { }
2206
2207 explicit
2208 param_type(_RealType __m, _RealType __s = _RealType(1))
2209 : _M_m(__m), _M_s(__s)
2210 { }
2211
2212 _RealType
2213 m() const
2214 { return _M_m; }
2215
2216 _RealType
2217 s() const
2218 { return _M_s; }
2219
2220 friend bool
2221 operator==(const param_type& __p1, const param_type& __p2)
2222 { return __p1._M_m == __p2._M_m && __p1._M_s == __p2._M_s; }
2223
2224 friend bool
2225 operator!=(const param_type& __p1, const param_type& __p2)
2226 { return !(__p1 == __p2); }
2227
2228 private:
2229 _RealType _M_m;
2230 _RealType _M_s;
2231 };
2232
2233 lognormal_distribution() : lognormal_distribution(0.0) { }
2234
2235 explicit
2236 lognormal_distribution(_RealType __m, _RealType __s = _RealType(1))
2237 : _M_param(__m, __s), _M_nd()
2238 { }
2239
2240 explicit
2241 lognormal_distribution(const param_type& __p)
2242 : _M_param(__p), _M_nd()
2243 { }
2244
2245 /**
2246 * Resets the distribution state.
2247 */
2248 void
2249 reset()
2250 { _M_nd.reset(); }
2251
2252 /**
2253 *
2254 */
2255 _RealType
2256 m() const
2257 { return _M_param.m(); }
2258
2259 _RealType
2260 s() const
2261 { return _M_param.s(); }
2262
2263 /**
2264 * @brief Returns the parameter set of the distribution.
2265 */
2266 param_type
2267 param() const
2268 { return _M_param; }
2269
2270 /**
2271 * @brief Sets the parameter set of the distribution.
2272 * @param __param The new parameter set of the distribution.
2273 */
2274 void
2275 param(const param_type& __param)
2276 { _M_param = __param; }
2277
2278 /**
2279 * @brief Returns the greatest lower bound value of the distribution.
2280 */
2281 result_type
2282 min() const
2283 { return result_type(0); }
2284
2285 /**
2286 * @brief Returns the least upper bound value of the distribution.
2287 */
2288 result_type
2289 max() const
2290 { return std::numeric_limits<result_type>::max(); }
2291
2292 /**
2293 * @brief Generating functions.
2294 */
2295 template<typename _UniformRandomNumberGenerator>
2296 result_type
2297 operator()(_UniformRandomNumberGenerator& __urng)
2298 { return this->operator()(__urng, _M_param); }
2299
2300 template<typename _UniformRandomNumberGenerator>
2301 result_type
2302 operator()(_UniformRandomNumberGenerator& __urng,
2303 const param_type& __p)
2304 { return std::exp(__p.s() * _M_nd(__urng) + __p.m()); }
2305
2306 template<typename _ForwardIterator,
2307 typename _UniformRandomNumberGenerator>
2308 void
2309 __generate(_ForwardIterator __f, _ForwardIterator __t,
2310 _UniformRandomNumberGenerator& __urng)
2311 { this->__generate(__f, __t, __urng, _M_param); }
2312
2313 template<typename _ForwardIterator,
2314 typename _UniformRandomNumberGenerator>
2315 void
2316 __generate(_ForwardIterator __f, _ForwardIterator __t,
2317 _UniformRandomNumberGenerator& __urng,
2318 const param_type& __p)
2319 { this->__generate_impl(__f, __t, __urng, __p); }
2320
2321 template<typename _UniformRandomNumberGenerator>
2322 void
2323 __generate(result_type* __f, result_type* __t,
2324 _UniformRandomNumberGenerator& __urng,
2325 const param_type& __p)
2326 { this->__generate_impl(__f, __t, __urng, __p); }
2327
2328 /**
2329 * @brief Return true if two lognormal distributions have
2330 * the same parameters and the sequences that would
2331 * be generated are equal.
2332 */
2333 friend bool
2334 operator==(const lognormal_distribution& __d1,
2335 const lognormal_distribution& __d2)
2336 { return (__d1._M_param == __d2._M_param
2337 && __d1._M_nd == __d2._M_nd); }
2338
2339 /**
2340 * @brief Inserts a %lognormal_distribution random number distribution
2341 * @p __x into the output stream @p __os.
2342 *
2343 * @param __os An output stream.
2344 * @param __x A %lognormal_distribution random number distribution.
2345 *
2346 * @returns The output stream with the state of @p __x inserted or in
2347 * an error state.
2348 */
2349 template<typename _RealType1, typename _CharT, typename _Traits>
2350 friend std::basic_ostream<_CharT, _Traits>&
2351 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
2352 const std::lognormal_distribution<_RealType1>& __x);
2353
2354 /**
2355 * @brief Extracts a %lognormal_distribution random number distribution
2356 * @p __x from the input stream @p __is.
2357 *
2358 * @param __is An input stream.
2359 * @param __x A %lognormal_distribution random number
2360 * generator engine.
2361 *
2362 * @returns The input stream with @p __x extracted or in an error state.
2363 */
2364 template<typename _RealType1, typename _CharT, typename _Traits>
2365 friend std::basic_istream<_CharT, _Traits>&
2366 operator>>(std::basic_istream<_CharT, _Traits>& __is,
2367 std::lognormal_distribution<_RealType1>& __x);
2368
2369 private:
2370 template<typename _ForwardIterator,
2371 typename _UniformRandomNumberGenerator>
2372 void
2373 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
2374 _UniformRandomNumberGenerator& __urng,
2375 const param_type& __p);
2376
2377 param_type _M_param;
2378
2379 std::normal_distribution<result_type> _M_nd;
2380 };
2381
2382 /**
2383 * @brief Return true if two lognormal distributions are different.
2384 */
2385 template<typename _RealType>
2386 inline bool
2387 operator!=(const std::lognormal_distribution<_RealType>& __d1,
2388 const std::lognormal_distribution<_RealType>& __d2)
2389 { return !(__d1 == __d2); }
2390
2391
2392 /**
2393 * @brief A gamma continuous distribution for random numbers.
2394 *
2395 * The formula for the gamma probability density function is:
2396 * @f[
2397 * p(x|\alpha,\beta) = \frac{1}{\beta\Gamma(\alpha)}
2398 * (x/\beta)^{\alpha - 1} e^{-x/\beta}
2399 * @f]
2400 */
2401 template<typename _RealType = double>
2402 class gamma_distribution
2403 {
2404 static_assert(std::is_floating_point<_RealType>::value,
2405 "result_type must be a floating point type");
2406
2407 public:
2408 /** The type of the range of the distribution. */
2409 typedef _RealType result_type;
2410
2411 /** Parameter type. */
2412 struct param_type
2413 {
2414 typedef gamma_distribution<_RealType> distribution_type;
2415 friend class gamma_distribution<_RealType>;
2416
2417 param_type() : param_type(1.0) { }
2418
2419 explicit
2420 param_type(_RealType __alpha_val, _RealType __beta_val = _RealType(1))
2421 : _M_alpha(__alpha_val), _M_beta(__beta_val)
2422 {
2423 __glibcxx_assert(_M_alpha > _RealType(0));
2424 _M_initialize();
2425 }
2426
2427 _RealType
2428 alpha() const
2429 { return _M_alpha; }
2430
2431 _RealType
2432 beta() const
2433 { return _M_beta; }
2434
2435 friend bool
2436 operator==(const param_type& __p1, const param_type& __p2)
2437 { return (__p1._M_alpha == __p2._M_alpha
2438 && __p1._M_beta == __p2._M_beta); }
2439
2440 friend bool
2441 operator!=(const param_type& __p1, const param_type& __p2)
2442 { return !(__p1 == __p2); }
2443
2444 private:
2445 void
2446 _M_initialize();
2447
2448 _RealType _M_alpha;
2449 _RealType _M_beta;
2450
2451 _RealType _M_malpha, _M_a2;
2452 };
2453
2454 public:
2455 /**
2456 * @brief Constructs a gamma distribution with parameters 1 and 1.
2457 */
2458 gamma_distribution() : gamma_distribution(1.0) { }
2459
2460 /**
2461 * @brief Constructs a gamma distribution with parameters
2462 * @f$\alpha@f$ and @f$\beta@f$.
2463 */
2464 explicit
2465 gamma_distribution(_RealType __alpha_val,
2466 _RealType __beta_val = _RealType(1))
2467 : _M_param(__alpha_val, __beta_val), _M_nd()
2468 { }
2469
2470 explicit
2471 gamma_distribution(const param_type& __p)
2472 : _M_param(__p), _M_nd()
2473 { }
2474
2475 /**
2476 * @brief Resets the distribution state.
2477 */
2478 void
2479 reset()
2480 { _M_nd.reset(); }
2481
2482 /**
2483 * @brief Returns the @f$\alpha@f$ of the distribution.
2484 */
2485 _RealType
2486 alpha() const
2487 { return _M_param.alpha(); }
2488
2489 /**
2490 * @brief Returns the @f$\beta@f$ of the distribution.
2491 */
2492 _RealType
2493 beta() const
2494 { return _M_param.beta(); }
2495
2496 /**
2497 * @brief Returns the parameter set of the distribution.
2498 */
2499 param_type
2500 param() const
2501 { return _M_param; }
2502
2503 /**
2504 * @brief Sets the parameter set of the distribution.
2505 * @param __param The new parameter set of the distribution.
2506 */
2507 void
2508 param(const param_type& __param)
2509 { _M_param = __param; }
2510
2511 /**
2512 * @brief Returns the greatest lower bound value of the distribution.
2513 */
2514 result_type
2515 min() const
2516 { return result_type(0); }
2517
2518 /**
2519 * @brief Returns the least upper bound value of the distribution.
2520 */
2521 result_type
2522 max() const
2523 { return std::numeric_limits<result_type>::max(); }
2524
2525 /**
2526 * @brief Generating functions.
2527 */
2528 template<typename _UniformRandomNumberGenerator>
2529 result_type
2530 operator()(_UniformRandomNumberGenerator& __urng)
2531 { return this->operator()(__urng, _M_param); }
2532
2533 template<typename _UniformRandomNumberGenerator>
2534 result_type
2535 operator()(_UniformRandomNumberGenerator& __urng,
2536 const param_type& __p);
2537
2538 template<typename _ForwardIterator,
2539 typename _UniformRandomNumberGenerator>
2540 void
2541 __generate(_ForwardIterator __f, _ForwardIterator __t,
2542 _UniformRandomNumberGenerator& __urng)
2543 { this->__generate(__f, __t, __urng, _M_param); }
2544
2545 template<typename _ForwardIterator,
2546 typename _UniformRandomNumberGenerator>
2547 void
2548 __generate(_ForwardIterator __f, _ForwardIterator __t,
2549 _UniformRandomNumberGenerator& __urng,
2550 const param_type& __p)
2551 { this->__generate_impl(__f, __t, __urng, __p); }
2552
2553 template<typename _UniformRandomNumberGenerator>
2554 void
2555 __generate(result_type* __f, result_type* __t,
2556 _UniformRandomNumberGenerator& __urng,
2557 const param_type& __p)
2558 { this->__generate_impl(__f, __t, __urng, __p); }
2559
2560 /**
2561 * @brief Return true if two gamma distributions have the same
2562 * parameters and the sequences that would be generated
2563 * are equal.
2564 */
2565 friend bool
2566 operator==(const gamma_distribution& __d1,
2567 const gamma_distribution& __d2)
2568 { return (__d1._M_param == __d2._M_param
2569 && __d1._M_nd == __d2._M_nd); }
2570
2571 /**
2572 * @brief Inserts a %gamma_distribution random number distribution
2573 * @p __x into the output stream @p __os.
2574 *
2575 * @param __os An output stream.
2576 * @param __x A %gamma_distribution random number distribution.
2577 *
2578 * @returns The output stream with the state of @p __x inserted or in
2579 * an error state.
2580 */
2581 template<typename _RealType1, typename _CharT, typename _Traits>
2582 friend std::basic_ostream<_CharT, _Traits>&
2583 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
2584 const std::gamma_distribution<_RealType1>& __x);
2585
2586 /**
2587 * @brief Extracts a %gamma_distribution random number distribution
2588 * @p __x from the input stream @p __is.
2589 *
2590 * @param __is An input stream.
2591 * @param __x A %gamma_distribution random number generator engine.
2592 *
2593 * @returns The input stream with @p __x extracted or in an error state.
2594 */
2595 template<typename _RealType1, typename _CharT, typename _Traits>
2596 friend std::basic_istream<_CharT, _Traits>&
2597 operator>>(std::basic_istream<_CharT, _Traits>& __is,
2598 std::gamma_distribution<_RealType1>& __x);
2599
2600 private:
2601 template<typename _ForwardIterator,
2602 typename _UniformRandomNumberGenerator>
2603 void
2604 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
2605 _UniformRandomNumberGenerator& __urng,
2606 const param_type& __p);
2607
2608 param_type _M_param;
2609
2610 std::normal_distribution<result_type> _M_nd;
2611 };
2612
2613 /**
2614 * @brief Return true if two gamma distributions are different.
2615 */
2616 template<typename _RealType>
2617 inline bool
2618 operator!=(const std::gamma_distribution<_RealType>& __d1,
2619 const std::gamma_distribution<_RealType>& __d2)
2620 { return !(__d1 == __d2); }
2621
2622
2623 /**
2624 * @brief A chi_squared_distribution random number distribution.
2625 *
2626 * The formula for the normal probability mass function is
2627 * @f$p(x|n) = \frac{x^{(n/2) - 1}e^{-x/2}}{\Gamma(n/2) 2^{n/2}}@f$
2628 */
2629 template<typename _RealType = double>
2630 class chi_squared_distribution
2631 {
2632 static_assert(std::is_floating_point<_RealType>::value,
2633 "result_type must be a floating point type");
2634
2635 public:
2636 /** The type of the range of the distribution. */
2637 typedef _RealType result_type;
2638
2639 /** Parameter type. */
2640 struct param_type
2641 {
2642 typedef chi_squared_distribution<_RealType> distribution_type;
2643
2644 param_type() : param_type(1) { }
2645
2646 explicit
2647 param_type(_RealType __n)
2648 : _M_n(__n)
2649 { }
2650
2651 _RealType
2652 n() const
2653 { return _M_n; }
2654
2655 friend bool
2656 operator==(const param_type& __p1, const param_type& __p2)
2657 { return __p1._M_n == __p2._M_n; }
2658
2659 friend bool
2660 operator!=(const param_type& __p1, const param_type& __p2)
2661 { return !(__p1 == __p2); }
2662
2663 private:
2664 _RealType _M_n;
2665 };
2666
2667 chi_squared_distribution() : chi_squared_distribution(1) { }
2668
2669 explicit
2670 chi_squared_distribution(_RealType __n)
2671 : _M_param(__n), _M_gd(__n / 2)
2672 { }
2673
2674 explicit
2675 chi_squared_distribution(const param_type& __p)
2676 : _M_param(__p), _M_gd(__p.n() / 2)
2677 { }
2678
2679 /**
2680 * @brief Resets the distribution state.
2681 */
2682 void
2683 reset()
2684 { _M_gd.reset(); }
2685
2686 /**
2687 *
2688 */
2689 _RealType
2690 n() const
2691 { return _M_param.n(); }
2692
2693 /**
2694 * @brief Returns the parameter set of the distribution.
2695 */
2696 param_type
2697 param() const
2698 { return _M_param; }
2699
2700 /**
2701 * @brief Sets the parameter set of the distribution.
2702 * @param __param The new parameter set of the distribution.
2703 */
2704 void
2705 param(const param_type& __param)
2706 {
2707 _M_param = __param;
2708 typedef typename std::gamma_distribution<result_type>::param_type
2709 param_type;
2710 _M_gd.param(param_type{__param.n() / 2});
2711 }
2712
2713 /**
2714 * @brief Returns the greatest lower bound value of the distribution.
2715 */
2716 result_type
2717 min() const
2718 { return result_type(0); }
2719
2720 /**
2721 * @brief Returns the least upper bound value of the distribution.
2722 */
2723 result_type
2724 max() const
2725 { return std::numeric_limits<result_type>::max(); }
2726
2727 /**
2728 * @brief Generating functions.
2729 */
2730 template<typename _UniformRandomNumberGenerator>
2731 result_type
2732 operator()(_UniformRandomNumberGenerator& __urng)
2733 { return 2 * _M_gd(__urng); }
2734
2735 template<typename _UniformRandomNumberGenerator>
2736 result_type
2737 operator()(_UniformRandomNumberGenerator& __urng,
2738 const param_type& __p)
2739 {
2740 typedef typename std::gamma_distribution<result_type>::param_type
2741 param_type;
2742 return 2 * _M_gd(__urng, param_type(__p.n() / 2));
2743 }
2744
2745 template<typename _ForwardIterator,
2746 typename _UniformRandomNumberGenerator>
2747 void
2748 __generate(_ForwardIterator __f, _ForwardIterator __t,
2749 _UniformRandomNumberGenerator& __urng)
2750 { this->__generate_impl(__f, __t, __urng); }
2751
2752 template<typename _ForwardIterator,
2753 typename _UniformRandomNumberGenerator>
2754 void
2755 __generate(_ForwardIterator __f, _ForwardIterator __t,
2756 _UniformRandomNumberGenerator& __urng,
2757 const param_type& __p)
2758 { typename std::gamma_distribution<result_type>::param_type
2759 __p2(__p.n() / 2);
2760 this->__generate_impl(__f, __t, __urng, __p2); }
2761
2762 template<typename _UniformRandomNumberGenerator>
2763 void
2764 __generate(result_type* __f, result_type* __t,
2765 _UniformRandomNumberGenerator& __urng)
2766 { this->__generate_impl(__f, __t, __urng); }
2767
2768 template<typename _UniformRandomNumberGenerator>
2769 void
2770 __generate(result_type* __f, result_type* __t,
2771 _UniformRandomNumberGenerator& __urng,
2772 const param_type& __p)
2773 { typename std::gamma_distribution<result_type>::param_type
2774 __p2(__p.n() / 2);
2775 this->__generate_impl(__f, __t, __urng, __p2); }
2776
2777 /**
2778 * @brief Return true if two Chi-squared distributions have
2779 * the same parameters and the sequences that would be
2780 * generated are equal.
2781 */
2782 friend bool
2783 operator==(const chi_squared_distribution& __d1,
2784 const chi_squared_distribution& __d2)
2785 { return __d1._M_param == __d2._M_param && __d1._M_gd == __d2._M_gd; }
2786
2787 /**
2788 * @brief Inserts a %chi_squared_distribution random number distribution
2789 * @p __x into the output stream @p __os.
2790 *
2791 * @param __os An output stream.
2792 * @param __x A %chi_squared_distribution random number distribution.
2793 *
2794 * @returns The output stream with the state of @p __x inserted or in
2795 * an error state.
2796 */
2797 template<typename _RealType1, typename _CharT, typename _Traits>
2798 friend std::basic_ostream<_CharT, _Traits>&
2799 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
2800 const std::chi_squared_distribution<_RealType1>& __x);
2801
2802 /**
2803 * @brief Extracts a %chi_squared_distribution random number distribution
2804 * @p __x from the input stream @p __is.
2805 *
2806 * @param __is An input stream.
2807 * @param __x A %chi_squared_distribution random number
2808 * generator engine.
2809 *
2810 * @returns The input stream with @p __x extracted or in an error state.
2811 */
2812 template<typename _RealType1, typename _CharT, typename _Traits>
2813 friend std::basic_istream<_CharT, _Traits>&
2814 operator>>(std::basic_istream<_CharT, _Traits>& __is,
2815 std::chi_squared_distribution<_RealType1>& __x);
2816
2817 private:
2818 template<typename _ForwardIterator,
2819 typename _UniformRandomNumberGenerator>
2820 void
2821 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
2822 _UniformRandomNumberGenerator& __urng);
2823
2824 template<typename _ForwardIterator,
2825 typename _UniformRandomNumberGenerator>
2826 void
2827 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
2828 _UniformRandomNumberGenerator& __urng,
2829 const typename
2830 std::gamma_distribution<result_type>::param_type& __p);
2831
2832 param_type _M_param;
2833
2834 std::gamma_distribution<result_type> _M_gd;
2835 };
2836
2837 /**
2838 * @brief Return true if two Chi-squared distributions are different.
2839 */
2840 template<typename _RealType>
2841 inline bool
2842 operator!=(const std::chi_squared_distribution<_RealType>& __d1,
2843 const std::chi_squared_distribution<_RealType>& __d2)
2844 { return !(__d1 == __d2); }
2845
2846
2847 /**
2848 * @brief A cauchy_distribution random number distribution.
2849 *
2850 * The formula for the normal probability mass function is
2851 * @f$p(x|a,b) = (\pi b (1 + (\frac{x-a}{b})^2))^{-1}@f$
2852 */
2853 template<typename _RealType = double>
2854 class cauchy_distribution
2855 {
2856 static_assert(std::is_floating_point<_RealType>::value,
2857 "result_type must be a floating point type");
2858
2859 public:
2860 /** The type of the range of the distribution. */
2861 typedef _RealType result_type;
2862
2863 /** Parameter type. */
2864 struct param_type
2865 {
2866 typedef cauchy_distribution<_RealType> distribution_type;
2867
2868 param_type() : param_type(0) { }
2869
2870 explicit
2871 param_type(_RealType __a, _RealType __b = _RealType(1))
2872 : _M_a(__a), _M_b(__b)
2873 { }
2874
2875 _RealType
2876 a() const
2877 { return _M_a; }
2878
2879 _RealType
2880 b() const
2881 { return _M_b; }
2882
2883 friend bool
2884 operator==(const param_type& __p1, const param_type& __p2)
2885 { return __p1._M_a == __p2._M_a && __p1._M_b == __p2._M_b; }
2886
2887 friend bool
2888 operator!=(const param_type& __p1, const param_type& __p2)
2889 { return !(__p1 == __p2); }
2890
2891 private:
2892 _RealType _M_a;
2893 _RealType _M_b;
2894 };
2895
2896 cauchy_distribution() : cauchy_distribution(0.0) { }
2897
2898 explicit
2899 cauchy_distribution(_RealType __a, _RealType __b = 1.0)
2900 : _M_param(__a, __b)
2901 { }
2902
2903 explicit
2904 cauchy_distribution(const param_type& __p)
2905 : _M_param(__p)
2906 { }
2907
2908 /**
2909 * @brief Resets the distribution state.
2910 */
2911 void
2912 reset()
2913 { }
2914
2915 /**
2916 *
2917 */
2918 _RealType
2919 a() const
2920 { return _M_param.a(); }
2921
2922 _RealType
2923 b() const
2924 { return _M_param.b(); }
2925
2926 /**
2927 * @brief Returns the parameter set of the distribution.
2928 */
2929 param_type
2930 param() const
2931 { return _M_param; }
2932
2933 /**
2934 * @brief Sets the parameter set of the distribution.
2935 * @param __param The new parameter set of the distribution.
2936 */
2937 void
2938 param(const param_type& __param)
2939 { _M_param = __param; }
2940
2941 /**
2942 * @brief Returns the greatest lower bound value of the distribution.
2943 */
2944 result_type
2945 min() const
2946 { return std::numeric_limits<result_type>::lowest(); }
2947
2948 /**
2949 * @brief Returns the least upper bound value of the distribution.
2950 */
2951 result_type
2952 max() const
2953 { return std::numeric_limits<result_type>::max(); }
2954
2955 /**
2956 * @brief Generating functions.
2957 */
2958 template<typename _UniformRandomNumberGenerator>
2959 result_type
2960 operator()(_UniformRandomNumberGenerator& __urng)
2961 { return this->operator()(__urng, _M_param); }
2962
2963 template<typename _UniformRandomNumberGenerator>
2964 result_type
2965 operator()(_UniformRandomNumberGenerator& __urng,
2966 const param_type& __p);
2967
2968 template<typename _ForwardIterator,
2969 typename _UniformRandomNumberGenerator>
2970 void
2971 __generate(_ForwardIterator __f, _ForwardIterator __t,
2972 _UniformRandomNumberGenerator& __urng)
2973 { this->__generate(__f, __t, __urng, _M_param); }
2974
2975 template<typename _ForwardIterator,
2976 typename _UniformRandomNumberGenerator>
2977 void
2978 __generate(_ForwardIterator __f, _ForwardIterator __t,
2979 _UniformRandomNumberGenerator& __urng,
2980 const param_type& __p)
2981 { this->__generate_impl(__f, __t, __urng, __p); }
2982
2983 template<typename _UniformRandomNumberGenerator>
2984 void
2985 __generate(result_type* __f, result_type* __t,
2986 _UniformRandomNumberGenerator& __urng,
2987 const param_type& __p)
2988 { this->__generate_impl(__f, __t, __urng, __p); }
2989
2990 /**
2991 * @brief Return true if two Cauchy distributions have
2992 * the same parameters.
2993 */
2994 friend bool
2995 operator==(const cauchy_distribution& __d1,
2996 const cauchy_distribution& __d2)
2997 { return __d1._M_param == __d2._M_param; }
2998
2999 private:
3000 template<typename _ForwardIterator,
3001 typename _UniformRandomNumberGenerator>
3002 void
3003 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
3004 _UniformRandomNumberGenerator& __urng,
3005 const param_type& __p);
3006
3007 param_type _M_param;
3008 };
3009
3010 /**
3011 * @brief Return true if two Cauchy distributions have
3012 * different parameters.
3013 */
3014 template<typename _RealType>
3015 inline bool
3016 operator!=(const std::cauchy_distribution<_RealType>& __d1,
3017 const std::cauchy_distribution<_RealType>& __d2)
3018 { return !(__d1 == __d2); }
3019
3020 /**
3021 * @brief Inserts a %cauchy_distribution random number distribution
3022 * @p __x into the output stream @p __os.
3023 *
3024 * @param __os An output stream.
3025 * @param __x A %cauchy_distribution random number distribution.
3026 *
3027 * @returns The output stream with the state of @p __x inserted or in
3028 * an error state.
3029 */
3030 template<typename _RealType, typename _CharT, typename _Traits>
3031 std::basic_ostream<_CharT, _Traits>&
3032 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
3033 const std::cauchy_distribution<_RealType>& __x);
3034
3035 /**
3036 * @brief Extracts a %cauchy_distribution random number distribution
3037 * @p __x from the input stream @p __is.
3038 *
3039 * @param __is An input stream.
3040 * @param __x A %cauchy_distribution random number
3041 * generator engine.
3042 *
3043 * @returns The input stream with @p __x extracted or in an error state.
3044 */
3045 template<typename _RealType, typename _CharT, typename _Traits>
3046 std::basic_istream<_CharT, _Traits>&
3047 operator>>(std::basic_istream<_CharT, _Traits>& __is,
3048 std::cauchy_distribution<_RealType>& __x);
3049
3050
3051 /**
3052 * @brief A fisher_f_distribution random number distribution.
3053 *
3054 * The formula for the normal probability mass function is
3055 * @f[
3056 * p(x|m,n) = \frac{\Gamma((m+n)/2)}{\Gamma(m/2)\Gamma(n/2)}
3057 * (\frac{m}{n})^{m/2} x^{(m/2)-1}
3058 * (1 + \frac{mx}{n})^{-(m+n)/2}
3059 * @f]
3060 */
3061 template<typename _RealType = double>
3062 class fisher_f_distribution
3063 {
3064 static_assert(std::is_floating_point<_RealType>::value,
3065 "result_type must be a floating point type");
3066
3067 public:
3068 /** The type of the range of the distribution. */
3069 typedef _RealType result_type;
3070
3071 /** Parameter type. */
3072 struct param_type
3073 {
3074 typedef fisher_f_distribution<_RealType> distribution_type;
3075
3076 param_type() : param_type(1) { }
3077
3078 explicit
3079 param_type(_RealType __m, _RealType __n = _RealType(1))
3080 : _M_m(__m), _M_n(__n)
3081 { }
3082
3083 _RealType
3084 m() const
3085 { return _M_m; }
3086
3087 _RealType
3088 n() const
3089 { return _M_n; }
3090
3091 friend bool
3092 operator==(const param_type& __p1, const param_type& __p2)
3093 { return __p1._M_m == __p2._M_m && __p1._M_n == __p2._M_n; }
3094
3095 friend bool
3096 operator!=(const param_type& __p1, const param_type& __p2)
3097 { return !(__p1 == __p2); }
3098
3099 private:
3100 _RealType _M_m;
3101 _RealType _M_n;
3102 };
3103
3104 fisher_f_distribution() : fisher_f_distribution(1.0) { }
3105
3106 explicit
3107 fisher_f_distribution(_RealType __m,
3108 _RealType __n = _RealType(1))
3109 : _M_param(__m, __n), _M_gd_x(__m / 2), _M_gd_y(__n / 2)
3110 { }
3111
3112 explicit
3113 fisher_f_distribution(const param_type& __p)
3114 : _M_param(__p), _M_gd_x(__p.m() / 2), _M_gd_y(__p.n() / 2)
3115 { }
3116
3117 /**
3118 * @brief Resets the distribution state.
3119 */
3120 void
3121 reset()
3122 {
3123 _M_gd_x.reset();
3124 _M_gd_y.reset();
3125 }
3126
3127 /**
3128 *
3129 */
3130 _RealType
3131 m() const
3132 { return _M_param.m(); }
3133
3134 _RealType
3135 n() const
3136 { return _M_param.n(); }
3137
3138 /**
3139 * @brief Returns the parameter set of the distribution.
3140 */
3141 param_type
3142 param() const
3143 { return _M_param; }
3144
3145 /**
3146 * @brief Sets the parameter set of the distribution.
3147 * @param __param The new parameter set of the distribution.
3148 */
3149 void
3150 param(const param_type& __param)
3151 { _M_param = __param; }
3152
3153 /**
3154 * @brief Returns the greatest lower bound value of the distribution.
3155 */
3156 result_type
3157 min() const
3158 { return result_type(0); }
3159
3160 /**
3161 * @brief Returns the least upper bound value of the distribution.
3162 */
3163 result_type
3164 max() const
3165 { return std::numeric_limits<result_type>::max(); }
3166
3167 /**
3168 * @brief Generating functions.
3169 */
3170 template<typename _UniformRandomNumberGenerator>
3171 result_type
3172 operator()(_UniformRandomNumberGenerator& __urng)
3173 { return (_M_gd_x(__urng) * n()) / (_M_gd_y(__urng) * m()); }
3174
3175 template<typename _UniformRandomNumberGenerator>
3176 result_type
3177 operator()(_UniformRandomNumberGenerator& __urng,
3178 const param_type& __p)
3179 {
3180 typedef typename std::gamma_distribution<result_type>::param_type
3181 param_type;
3182 return ((_M_gd_x(__urng, param_type(__p.m() / 2)) * n())
3183 / (_M_gd_y(__urng, param_type(__p.n() / 2)) * m()));
3184 }
3185
3186 template<typename _ForwardIterator,
3187 typename _UniformRandomNumberGenerator>
3188 void
3189 __generate(_ForwardIterator __f, _ForwardIterator __t,
3190 _UniformRandomNumberGenerator& __urng)
3191 { this->__generate_impl(__f, __t, __urng); }
3192
3193 template<typename _ForwardIterator,
3194 typename _UniformRandomNumberGenerator>
3195 void
3196 __generate(_ForwardIterator __f, _ForwardIterator __t,
3197 _UniformRandomNumberGenerator& __urng,
3198 const param_type& __p)
3199 { this->__generate_impl(__f, __t, __urng, __p); }
3200
3201 template<typename _UniformRandomNumberGenerator>
3202 void
3203 __generate(result_type* __f, result_type* __t,
3204 _UniformRandomNumberGenerator& __urng)
3205 { this->__generate_impl(__f, __t, __urng); }
3206
3207 template<typename _UniformRandomNumberGenerator>
3208 void
3209 __generate(result_type* __f, result_type* __t,
3210 _UniformRandomNumberGenerator& __urng,
3211 const param_type& __p)
3212 { this->__generate_impl(__f, __t, __urng, __p); }
3213
3214 /**
3215 * @brief Return true if two Fisher f distributions have
3216 * the same parameters and the sequences that would
3217 * be generated are equal.
3218 */
3219 friend bool
3220 operator==(const fisher_f_distribution& __d1,
3221 const fisher_f_distribution& __d2)
3222 { return (__d1._M_param == __d2._M_param
3223 && __d1._M_gd_x == __d2._M_gd_x
3224 && __d1._M_gd_y == __d2._M_gd_y); }
3225
3226 /**
3227 * @brief Inserts a %fisher_f_distribution random number distribution
3228 * @p __x into the output stream @p __os.
3229 *
3230 * @param __os An output stream.
3231 * @param __x A %fisher_f_distribution random number distribution.
3232 *
3233 * @returns The output stream with the state of @p __x inserted or in
3234 * an error state.
3235 */
3236 template<typename _RealType1, typename _CharT, typename _Traits>
3237 friend std::basic_ostream<_CharT, _Traits>&
3238 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
3239 const std::fisher_f_distribution<_RealType1>& __x);
3240
3241 /**
3242 * @brief Extracts a %fisher_f_distribution random number distribution
3243 * @p __x from the input stream @p __is.
3244 *
3245 * @param __is An input stream.
3246 * @param __x A %fisher_f_distribution random number
3247 * generator engine.
3248 *
3249 * @returns The input stream with @p __x extracted or in an error state.
3250 */
3251 template<typename _RealType1, typename _CharT, typename _Traits>
3252 friend std::basic_istream<_CharT, _Traits>&
3253 operator>>(std::basic_istream<_CharT, _Traits>& __is,
3254 std::fisher_f_distribution<_RealType1>& __x);
3255
3256 private:
3257 template<typename _ForwardIterator,
3258 typename _UniformRandomNumberGenerator>
3259 void
3260 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
3261 _UniformRandomNumberGenerator& __urng);
3262
3263 template<typename _ForwardIterator,
3264 typename _UniformRandomNumberGenerator>
3265 void
3266 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
3267 _UniformRandomNumberGenerator& __urng,
3268 const param_type& __p);
3269
3270 param_type _M_param;
3271
3272 std::gamma_distribution<result_type> _M_gd_x, _M_gd_y;
3273 };
3274
3275 /**
3276 * @brief Return true if two Fisher f distributions are different.
3277 */
3278 template<typename _RealType>
3279 inline bool
3280 operator!=(const std::fisher_f_distribution<_RealType>& __d1,
3281 const std::fisher_f_distribution<_RealType>& __d2)
3282 { return !(__d1 == __d2); }
3283
3284 /**
3285 * @brief A student_t_distribution random number distribution.
3286 *
3287 * The formula for the normal probability mass function is:
3288 * @f[
3289 * p(x|n) = \frac{1}{\sqrt(n\pi)} \frac{\Gamma((n+1)/2)}{\Gamma(n/2)}
3290 * (1 + \frac{x^2}{n}) ^{-(n+1)/2}
3291 * @f]
3292 */
3293 template<typename _RealType = double>
3294 class student_t_distribution
3295 {
3296 static_assert(std::is_floating_point<_RealType>::value,
3297 "result_type must be a floating point type");
3298
3299 public:
3300 /** The type of the range of the distribution. */
3301 typedef _RealType result_type;
3302
3303 /** Parameter type. */
3304 struct param_type
3305 {
3306 typedef student_t_distribution<_RealType> distribution_type;
3307
3308 param_type() : param_type(1) { }
3309
3310 explicit
3311 param_type(_RealType __n)
3312 : _M_n(__n)
3313 { }
3314
3315 _RealType
3316 n() const
3317 { return _M_n; }
3318
3319 friend bool
3320 operator==(const param_type& __p1, const param_type& __p2)
3321 { return __p1._M_n == __p2._M_n; }
3322
3323 friend bool
3324 operator!=(const param_type& __p1, const param_type& __p2)
3325 { return !(__p1 == __p2); }
3326
3327 private:
3328 _RealType _M_n;
3329 };
3330
3331 student_t_distribution() : student_t_distribution(1.0) { }
3332
3333 explicit
3334 student_t_distribution(_RealType __n)
3335 : _M_param(__n), _M_nd(), _M_gd(__n / 2, 2)
3336 { }
3337
3338 explicit
3339 student_t_distribution(const param_type& __p)
3340 : _M_param(__p), _M_nd(), _M_gd(__p.n() / 2, 2)
3341 { }
3342
3343 /**
3344 * @brief Resets the distribution state.
3345 */
3346 void
3347 reset()
3348 {
3349 _M_nd.reset();
3350 _M_gd.reset();
3351 }
3352
3353 /**
3354 *
3355 */
3356 _RealType
3357 n() const
3358 { return _M_param.n(); }
3359
3360 /**
3361 * @brief Returns the parameter set of the distribution.
3362 */
3363 param_type
3364 param() const
3365 { return _M_param; }
3366
3367 /**
3368 * @brief Sets the parameter set of the distribution.
3369 * @param __param The new parameter set of the distribution.
3370 */
3371 void
3372 param(const param_type& __param)
3373 { _M_param = __param; }
3374
3375 /**
3376 * @brief Returns the greatest lower bound value of the distribution.
3377 */
3378 result_type
3379 min() const
3380 { return std::numeric_limits<result_type>::lowest(); }
3381
3382 /**
3383 * @brief Returns the least upper bound value of the distribution.
3384 */
3385 result_type
3386 max() const
3387 { return std::numeric_limits<result_type>::max(); }
3388
3389 /**
3390 * @brief Generating functions.
3391 */
3392 template<typename _UniformRandomNumberGenerator>
3393 result_type
3394 operator()(_UniformRandomNumberGenerator& __urng)
3395 { return _M_nd(__urng) * std::sqrt(n() / _M_gd(__urng)); }
3396
3397 template<typename _UniformRandomNumberGenerator>
3398 result_type
3399 operator()(_UniformRandomNumberGenerator& __urng,
3400 const param_type& __p)
3401 {
3402 typedef typename std::gamma_distribution<result_type>::param_type
3403 param_type;
3404
3405 const result_type __g = _M_gd(__urng, param_type(__p.n() / 2, 2));
3406 return _M_nd(__urng) * std::sqrt(__p.n() / __g);
3407 }
3408
3409 template<typename _ForwardIterator,
3410 typename _UniformRandomNumberGenerator>
3411 void
3412 __generate(_ForwardIterator __f, _ForwardIterator __t,
3413 _UniformRandomNumberGenerator& __urng)
3414 { this->__generate_impl(__f, __t, __urng); }
3415
3416 template<typename _ForwardIterator,
3417 typename _UniformRandomNumberGenerator>
3418 void
3419 __generate(_ForwardIterator __f, _ForwardIterator __t,
3420 _UniformRandomNumberGenerator& __urng,
3421 const param_type& __p)
3422 { this->__generate_impl(__f, __t, __urng, __p); }
3423
3424 template<typename _UniformRandomNumberGenerator>
3425 void
3426 __generate(result_type* __f, result_type* __t,
3427 _UniformRandomNumberGenerator& __urng)
3428 { this->__generate_impl(__f, __t, __urng); }
3429
3430 template<typename _UniformRandomNumberGenerator>
3431 void
3432 __generate(result_type* __f, result_type* __t,
3433 _UniformRandomNumberGenerator& __urng,
3434 const param_type& __p)
3435 { this->__generate_impl(__f, __t, __urng, __p); }
3436
3437 /**
3438 * @brief Return true if two Student t distributions have
3439 * the same parameters and the sequences that would
3440 * be generated are equal.
3441 */
3442 friend bool
3443 operator==(const student_t_distribution& __d1,
3444 const student_t_distribution& __d2)
3445 { return (__d1._M_param == __d2._M_param
3446 && __d1._M_nd == __d2._M_nd && __d1._M_gd == __d2._M_gd); }
3447
3448 /**
3449 * @brief Inserts a %student_t_distribution random number distribution
3450 * @p __x into the output stream @p __os.
3451 *
3452 * @param __os An output stream.
3453 * @param __x A %student_t_distribution random number distribution.
3454 *
3455 * @returns The output stream with the state of @p __x inserted or in
3456 * an error state.
3457 */
3458 template<typename _RealType1, typename _CharT, typename _Traits>
3459 friend std::basic_ostream<_CharT, _Traits>&
3460 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
3461 const std::student_t_distribution<_RealType1>& __x);
3462
3463 /**
3464 * @brief Extracts a %student_t_distribution random number distribution
3465 * @p __x from the input stream @p __is.
3466 *
3467 * @param __is An input stream.
3468 * @param __x A %student_t_distribution random number
3469 * generator engine.
3470 *
3471 * @returns The input stream with @p __x extracted or in an error state.
3472 */
3473 template<typename _RealType1, typename _CharT, typename _Traits>
3474 friend std::basic_istream<_CharT, _Traits>&
3475 operator>>(std::basic_istream<_CharT, _Traits>& __is,
3476 std::student_t_distribution<_RealType1>& __x);
3477
3478 private:
3479 template<typename _ForwardIterator,
3480 typename _UniformRandomNumberGenerator>
3481 void
3482 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
3483 _UniformRandomNumberGenerator& __urng);
3484 template<typename _ForwardIterator,
3485 typename _UniformRandomNumberGenerator>
3486 void
3487 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
3488 _UniformRandomNumberGenerator& __urng,
3489 const param_type& __p);
3490
3491 param_type _M_param;
3492
3493 std::normal_distribution<result_type> _M_nd;
3494 std::gamma_distribution<result_type> _M_gd;
3495 };
3496
3497 /**
3498 * @brief Return true if two Student t distributions are different.
3499 */
3500 template<typename _RealType>
3501 inline bool
3502 operator!=(const std::student_t_distribution<_RealType>& __d1,
3503 const std::student_t_distribution<_RealType>& __d2)
3504 { return !(__d1 == __d2); }
3505
3506
3507 /* @} */ // group random_distributions_normal
3508
3509 /**
3510 * @addtogroup random_distributions_bernoulli Bernoulli Distributions
3511 * @ingroup random_distributions
3512 * @{
3513 */
3514
3515 /**
3516 * @brief A Bernoulli random number distribution.
3517 *
3518 * Generates a sequence of true and false values with likelihood @f$p@f$
3519 * that true will come up and @f$(1 - p)@f$ that false will appear.
3520 */
3521 class bernoulli_distribution
3522 {
3523 public:
3524 /** The type of the range of the distribution. */
3525 typedef bool result_type;
3526
3527 /** Parameter type. */
3528 struct param_type
3529 {
3530 typedef bernoulli_distribution distribution_type;
3531
3532 param_type() : param_type(0.5) { }
3533
3534 explicit
3535 param_type(double __p)
3536 : _M_p(__p)
3537 {
3538 __glibcxx_assert((_M_p >= 0.0) && (_M_p <= 1.0));
3539 }
3540
3541 double
3542 p() const
3543 { return _M_p; }
3544
3545 friend bool
3546 operator==(const param_type& __p1, const param_type& __p2)
3547 { return __p1._M_p == __p2._M_p; }
3548
3549 friend bool
3550 operator!=(const param_type& __p1, const param_type& __p2)
3551 { return !(__p1 == __p2); }
3552
3553 private:
3554 double _M_p;
3555 };
3556
3557 public:
3558 /**
3559 * @brief Constructs a Bernoulli distribution with likelihood 0.5.
3560 */
3561 bernoulli_distribution() : bernoulli_distribution(0.5) { }
3562
3563 /**
3564 * @brief Constructs a Bernoulli distribution with likelihood @p p.
3565 *
3566 * @param __p [IN] The likelihood of a true result being returned.
3567 * Must be in the interval @f$[0, 1]@f$.
3568 */
3569 explicit
3570 bernoulli_distribution(double __p)
3571 : _M_param(__p)
3572 { }
3573
3574 explicit
3575 bernoulli_distribution(const param_type& __p)
3576 : _M_param(__p)
3577 { }
3578
3579 /**
3580 * @brief Resets the distribution state.
3581 *
3582 * Does nothing for a Bernoulli distribution.
3583 */
3584 void
3585 reset() { }
3586
3587 /**
3588 * @brief Returns the @p p parameter of the distribution.
3589 */
3590 double
3591 p() const
3592 { return _M_param.p(); }
3593
3594 /**
3595 * @brief Returns the parameter set of the distribution.
3596 */
3597 param_type
3598 param() const
3599 { return _M_param; }
3600
3601 /**
3602 * @brief Sets the parameter set of the distribution.
3603 * @param __param The new parameter set of the distribution.
3604 */
3605 void
3606 param(const param_type& __param)
3607 { _M_param = __param; }
3608
3609 /**
3610 * @brief Returns the greatest lower bound value of the distribution.
3611 */
3612 result_type
3613 min() const
3614 { return std::numeric_limits<result_type>::min(); }
3615
3616 /**
3617 * @brief Returns the least upper bound value of the distribution.
3618 */
3619 result_type
3620 max() const
3621 { return std::numeric_limits<result_type>::max(); }
3622
3623 /**
3624 * @brief Generating functions.
3625 */
3626 template<typename _UniformRandomNumberGenerator>
3627 result_type
3628 operator()(_UniformRandomNumberGenerator& __urng)
3629 { return this->operator()(__urng, _M_param); }
3630
3631 template<typename _UniformRandomNumberGenerator>
3632 result_type
3633 operator()(_UniformRandomNumberGenerator& __urng,
3634 const param_type& __p)
3635 {
3636 __detail::_Adaptor<_UniformRandomNumberGenerator, double>
3637 __aurng(__urng);
3638 if ((__aurng() - __aurng.min())
3639 < __p.p() * (__aurng.max() - __aurng.min()))
3640 return true;
3641 return false;
3642 }
3643
3644 template<typename _ForwardIterator,
3645 typename _UniformRandomNumberGenerator>
3646 void
3647 __generate(_ForwardIterator __f, _ForwardIterator __t,
3648 _UniformRandomNumberGenerator& __urng)
3649 { this->__generate(__f, __t, __urng, _M_param); }
3650
3651 template<typename _ForwardIterator,
3652 typename _UniformRandomNumberGenerator>
3653 void
3654 __generate(_ForwardIterator __f, _ForwardIterator __t,
3655 _UniformRandomNumberGenerator& __urng, const param_type& __p)
3656 { this->__generate_impl(__f, __t, __urng, __p); }
3657
3658 template<typename _UniformRandomNumberGenerator>
3659 void
3660 __generate(result_type* __f, result_type* __t,
3661 _UniformRandomNumberGenerator& __urng,
3662 const param_type& __p)
3663 { this->__generate_impl(__f, __t, __urng, __p); }
3664
3665 /**
3666 * @brief Return true if two Bernoulli distributions have
3667 * the same parameters.
3668 */
3669 friend bool
3670 operator==(const bernoulli_distribution& __d1,
3671 const bernoulli_distribution& __d2)
3672 { return __d1._M_param == __d2._M_param; }
3673
3674 private:
3675 template<typename _ForwardIterator,
3676 typename _UniformRandomNumberGenerator>
3677 void
3678 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
3679 _UniformRandomNumberGenerator& __urng,
3680 const param_type& __p);
3681
3682 param_type _M_param;
3683 };
3684
3685 /**
3686 * @brief Return true if two Bernoulli distributions have
3687 * different parameters.
3688 */
3689 inline bool
3690 operator!=(const std::bernoulli_distribution& __d1,
3691 const std::bernoulli_distribution& __d2)
3692 { return !(__d1 == __d2); }
3693
3694 /**
3695 * @brief Inserts a %bernoulli_distribution random number distribution
3696 * @p __x into the output stream @p __os.
3697 *
3698 * @param __os An output stream.
3699 * @param __x A %bernoulli_distribution random number distribution.
3700 *
3701 * @returns The output stream with the state of @p __x inserted or in
3702 * an error state.
3703 */
3704 template<typename _CharT, typename _Traits>
3705 std::basic_ostream<_CharT, _Traits>&
3706 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
3707 const std::bernoulli_distribution& __x);
3708
3709 /**
3710 * @brief Extracts a %bernoulli_distribution random number distribution
3711 * @p __x from the input stream @p __is.
3712 *
3713 * @param __is An input stream.
3714 * @param __x A %bernoulli_distribution random number generator engine.
3715 *
3716 * @returns The input stream with @p __x extracted or in an error state.
3717 */
3718 template<typename _CharT, typename _Traits>
3719 inline std::basic_istream<_CharT, _Traits>&
3720 operator>>(std::basic_istream<_CharT, _Traits>& __is,
3721 std::bernoulli_distribution& __x)
3722 {
3723 double __p;
3724 if (__is >> __p)
3725 __x.param(bernoulli_distribution::param_type(__p));
3726 return __is;
3727 }
3728
3729
3730 /**
3731 * @brief A discrete binomial random number distribution.
3732 *
3733 * The formula for the binomial probability density function is
3734 * @f$p(i|t,p) = \binom{t}{i} p^i (1 - p)^{t - i}@f$ where @f$t@f$
3735 * and @f$p@f$ are the parameters of the distribution.
3736 */
3737 template<typename _IntType = int>
3738 class binomial_distribution
3739 {
3740 static_assert(std::is_integral<_IntType>::value,
3741 "result_type must be an integral type");
3742
3743 public:
3744 /** The type of the range of the distribution. */
3745 typedef _IntType result_type;
3746
3747 /** Parameter type. */
3748 struct param_type
3749 {
3750 typedef binomial_distribution<_IntType> distribution_type;
3751 friend class binomial_distribution<_IntType>;
3752
3753 param_type() : param_type(1) { }
3754
3755 explicit
3756 param_type(_IntType __t, double __p = 0.5)
3757 : _M_t(__t), _M_p(__p)
3758 {
3759 __glibcxx_assert((_M_t >= _IntType(0))
3760 && (_M_p >= 0.0)
3761 && (_M_p <= 1.0));
3762 _M_initialize();
3763 }
3764
3765 _IntType
3766 t() const
3767 { return _M_t; }
3768
3769 double
3770 p() const
3771 { return _M_p; }
3772
3773 friend bool
3774 operator==(const param_type& __p1, const param_type& __p2)
3775 { return __p1._M_t == __p2._M_t && __p1._M_p == __p2._M_p; }
3776
3777 friend bool
3778 operator!=(const param_type& __p1, const param_type& __p2)
3779 { return !(__p1 == __p2); }
3780
3781 private:
3782 void
3783 _M_initialize();
3784
3785 _IntType _M_t;
3786 double _M_p;
3787
3788 double _M_q;
3789 #if _GLIBCXX_USE_C99_MATH_TR1
3790 double _M_d1, _M_d2, _M_s1, _M_s2, _M_c,
3791 _M_a1, _M_a123, _M_s, _M_lf, _M_lp1p;
3792 #endif
3793 bool _M_easy;
3794 };
3795
3796 // constructors and member functions
3797
3798 binomial_distribution() : binomial_distribution(1) { }
3799
3800 explicit
3801 binomial_distribution(_IntType __t, double __p = 0.5)
3802 : _M_param(__t, __p), _M_nd()
3803 { }
3804
3805 explicit
3806 binomial_distribution(const param_type& __p)
3807 : _M_param(__p), _M_nd()
3808 { }
3809
3810 /**
3811 * @brief Resets the distribution state.
3812 */
3813 void
3814 reset()
3815 { _M_nd.reset(); }
3816
3817 /**
3818 * @brief Returns the distribution @p t parameter.
3819 */
3820 _IntType
3821 t() const
3822 { return _M_param.t(); }
3823
3824 /**
3825 * @brief Returns the distribution @p p parameter.
3826 */
3827 double
3828 p() const
3829 { return _M_param.p(); }
3830
3831 /**
3832 * @brief Returns the parameter set of the distribution.
3833 */
3834 param_type
3835 param() const
3836 { return _M_param; }
3837
3838 /**
3839 * @brief Sets the parameter set of the distribution.
3840 * @param __param The new parameter set of the distribution.
3841 */
3842 void
3843 param(const param_type& __param)
3844 { _M_param = __param; }
3845
3846 /**
3847 * @brief Returns the greatest lower bound value of the distribution.
3848 */
3849 result_type
3850 min() const
3851 { return 0; }
3852
3853 /**
3854 * @brief Returns the least upper bound value of the distribution.
3855 */
3856 result_type
3857 max() const
3858 { return _M_param.t(); }
3859
3860 /**
3861 * @brief Generating functions.
3862 */
3863 template<typename _UniformRandomNumberGenerator>
3864 result_type
3865 operator()(_UniformRandomNumberGenerator& __urng)
3866 { return this->operator()(__urng, _M_param); }
3867
3868 template<typename _UniformRandomNumberGenerator>
3869 result_type
3870 operator()(_UniformRandomNumberGenerator& __urng,
3871 const param_type& __p);
3872
3873 template<typename _ForwardIterator,
3874 typename _UniformRandomNumberGenerator>
3875 void
3876 __generate(_ForwardIterator __f, _ForwardIterator __t,
3877 _UniformRandomNumberGenerator& __urng)
3878 { this->__generate(__f, __t, __urng, _M_param); }
3879
3880 template<typename _ForwardIterator,
3881 typename _UniformRandomNumberGenerator>
3882 void
3883 __generate(_ForwardIterator __f, _ForwardIterator __t,
3884 _UniformRandomNumberGenerator& __urng,
3885 const param_type& __p)
3886 { this->__generate_impl(__f, __t, __urng, __p); }
3887
3888 template<typename _UniformRandomNumberGenerator>
3889 void
3890 __generate(result_type* __f, result_type* __t,
3891 _UniformRandomNumberGenerator& __urng,
3892 const param_type& __p)
3893 { this->__generate_impl(__f, __t, __urng, __p); }
3894
3895 /**
3896 * @brief Return true if two binomial distributions have
3897 * the same parameters and the sequences that would
3898 * be generated are equal.
3899 */
3900 friend bool
3901 operator==(const binomial_distribution& __d1,
3902 const binomial_distribution& __d2)
3903 #ifdef _GLIBCXX_USE_C99_MATH_TR1
3904 { return __d1._M_param == __d2._M_param && __d1._M_nd == __d2._M_nd; }
3905 #else
3906 { return __d1._M_param == __d2._M_param; }
3907 #endif
3908
3909 /**
3910 * @brief Inserts a %binomial_distribution random number distribution
3911 * @p __x into the output stream @p __os.
3912 *
3913 * @param __os An output stream.
3914 * @param __x A %binomial_distribution random number distribution.
3915 *
3916 * @returns The output stream with the state of @p __x inserted or in
3917 * an error state.
3918 */
3919 template<typename _IntType1,
3920 typename _CharT, typename _Traits>
3921 friend std::basic_ostream<_CharT, _Traits>&
3922 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
3923 const std::binomial_distribution<_IntType1>& __x);
3924
3925 /**
3926 * @brief Extracts a %binomial_distribution random number distribution
3927 * @p __x from the input stream @p __is.
3928 *
3929 * @param __is An input stream.
3930 * @param __x A %binomial_distribution random number generator engine.
3931 *
3932 * @returns The input stream with @p __x extracted or in an error
3933 * state.
3934 */
3935 template<typename _IntType1,
3936 typename _CharT, typename _Traits>
3937 friend std::basic_istream<_CharT, _Traits>&
3938 operator>>(std::basic_istream<_CharT, _Traits>& __is,
3939 std::binomial_distribution<_IntType1>& __x);
3940
3941 private:
3942 template<typename _ForwardIterator,
3943 typename _UniformRandomNumberGenerator>
3944 void
3945 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
3946 _UniformRandomNumberGenerator& __urng,
3947 const param_type& __p);
3948
3949 template<typename _UniformRandomNumberGenerator>
3950 result_type
3951 _M_waiting(_UniformRandomNumberGenerator& __urng,
3952 _IntType __t, double __q);
3953
3954 param_type _M_param;
3955
3956 // NB: Unused when _GLIBCXX_USE_C99_MATH_TR1 is undefined.
3957 std::normal_distribution<double> _M_nd;
3958 };
3959
3960 /**
3961 * @brief Return true if two binomial distributions are different.
3962 */
3963 template<typename _IntType>
3964 inline bool
3965 operator!=(const std::binomial_distribution<_IntType>& __d1,
3966 const std::binomial_distribution<_IntType>& __d2)
3967 { return !(__d1 == __d2); }
3968
3969
3970 /**
3971 * @brief A discrete geometric random number distribution.
3972 *
3973 * The formula for the geometric probability density function is
3974 * @f$p(i|p) = p(1 - p)^{i}@f$ where @f$p@f$ is the parameter of the
3975 * distribution.
3976 */
3977 template<typename _IntType = int>
3978 class geometric_distribution
3979 {
3980 static_assert(std::is_integral<_IntType>::value,
3981 "result_type must be an integral type");
3982
3983 public:
3984 /** The type of the range of the distribution. */
3985 typedef _IntType result_type;
3986
3987 /** Parameter type. */
3988 struct param_type
3989 {
3990 typedef geometric_distribution<_IntType> distribution_type;
3991 friend class geometric_distribution<_IntType>;
3992
3993 param_type() : param_type(0.5) { }
3994
3995 explicit
3996 param_type(double __p)
3997 : _M_p(__p)
3998 {
3999 __glibcxx_assert((_M_p > 0.0) && (_M_p < 1.0));
4000 _M_initialize();
4001 }
4002
4003 double
4004 p() const
4005 { return _M_p; }
4006
4007 friend bool
4008 operator==(const param_type& __p1, const param_type& __p2)
4009 { return __p1._M_p == __p2._M_p; }
4010
4011 friend bool
4012 operator!=(const param_type& __p1, const param_type& __p2)
4013 { return !(__p1 == __p2); }
4014
4015 private:
4016 void
4017 _M_initialize()
4018 { _M_log_1_p = std::log(1.0 - _M_p); }
4019
4020 double _M_p;
4021
4022 double _M_log_1_p;
4023 };
4024
4025 // constructors and member functions
4026
4027 geometric_distribution() : geometric_distribution(0.5) { }
4028
4029 explicit
4030 geometric_distribution(double __p)
4031 : _M_param(__p)
4032 { }
4033
4034 explicit
4035 geometric_distribution(const param_type& __p)
4036 : _M_param(__p)
4037 { }
4038
4039 /**
4040 * @brief Resets the distribution state.
4041 *
4042 * Does nothing for the geometric distribution.
4043 */
4044 void
4045 reset() { }
4046
4047 /**
4048 * @brief Returns the distribution parameter @p p.
4049 */
4050 double
4051 p() const
4052 { return _M_param.p(); }
4053
4054 /**
4055 * @brief Returns the parameter set of the distribution.
4056 */
4057 param_type
4058 param() const
4059 { return _M_param; }
4060
4061 /**
4062 * @brief Sets the parameter set of the distribution.
4063 * @param __param The new parameter set of the distribution.
4064 */
4065 void
4066 param(const param_type& __param)
4067 { _M_param = __param; }
4068
4069 /**
4070 * @brief Returns the greatest lower bound value of the distribution.
4071 */
4072 result_type
4073 min() const
4074 { return 0; }
4075
4076 /**
4077 * @brief Returns the least upper bound value of the distribution.
4078 */
4079 result_type
4080 max() const
4081 { return std::numeric_limits<result_type>::max(); }
4082
4083 /**
4084 * @brief Generating functions.
4085 */
4086 template<typename _UniformRandomNumberGenerator>
4087 result_type
4088 operator()(_UniformRandomNumberGenerator& __urng)
4089 { return this->operator()(__urng, _M_param); }
4090
4091 template<typename _UniformRandomNumberGenerator>
4092 result_type
4093 operator()(_UniformRandomNumberGenerator& __urng,
4094 const param_type& __p);
4095
4096 template<typename _ForwardIterator,
4097 typename _UniformRandomNumberGenerator>
4098 void
4099 __generate(_ForwardIterator __f, _ForwardIterator __t,
4100 _UniformRandomNumberGenerator& __urng)
4101 { this->__generate(__f, __t, __urng, _M_param); }
4102
4103 template<typename _ForwardIterator,
4104 typename _UniformRandomNumberGenerator>
4105 void
4106 __generate(_ForwardIterator __f, _ForwardIterator __t,
4107 _UniformRandomNumberGenerator& __urng,
4108 const param_type& __p)
4109 { this->__generate_impl(__f, __t, __urng, __p); }
4110
4111 template<typename _UniformRandomNumberGenerator>
4112 void
4113 __generate(result_type* __f, result_type* __t,
4114 _UniformRandomNumberGenerator& __urng,
4115 const param_type& __p)
4116 { this->__generate_impl(__f, __t, __urng, __p); }
4117
4118 /**
4119 * @brief Return true if two geometric distributions have
4120 * the same parameters.
4121 */
4122 friend bool
4123 operator==(const geometric_distribution& __d1,
4124 const geometric_distribution& __d2)
4125 { return __d1._M_param == __d2._M_param; }
4126
4127 private:
4128 template<typename _ForwardIterator,
4129 typename _UniformRandomNumberGenerator>
4130 void
4131 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
4132 _UniformRandomNumberGenerator& __urng,
4133 const param_type& __p);
4134
4135 param_type _M_param;
4136 };
4137
4138 /**
4139 * @brief Return true if two geometric distributions have
4140 * different parameters.
4141 */
4142 template<typename _IntType>
4143 inline bool
4144 operator!=(const std::geometric_distribution<_IntType>& __d1,
4145 const std::geometric_distribution<_IntType>& __d2)
4146 { return !(__d1 == __d2); }
4147
4148 /**
4149 * @brief Inserts a %geometric_distribution random number distribution
4150 * @p __x into the output stream @p __os.
4151 *
4152 * @param __os An output stream.
4153 * @param __x A %geometric_distribution random number distribution.
4154 *
4155 * @returns The output stream with the state of @p __x inserted or in
4156 * an error state.
4157 */
4158 template<typename _IntType,
4159 typename _CharT, typename _Traits>
4160 std::basic_ostream<_CharT, _Traits>&
4161 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
4162 const std::geometric_distribution<_IntType>& __x);
4163
4164 /**
4165 * @brief Extracts a %geometric_distribution random number distribution
4166 * @p __x from the input stream @p __is.
4167 *
4168 * @param __is An input stream.
4169 * @param __x A %geometric_distribution random number generator engine.
4170 *
4171 * @returns The input stream with @p __x extracted or in an error state.
4172 */
4173 template<typename _IntType,
4174 typename _CharT, typename _Traits>
4175 std::basic_istream<_CharT, _Traits>&
4176 operator>>(std::basic_istream<_CharT, _Traits>& __is,
4177 std::geometric_distribution<_IntType>& __x);
4178
4179
4180 /**
4181 * @brief A negative_binomial_distribution random number distribution.
4182 *
4183 * The formula for the negative binomial probability mass function is
4184 * @f$p(i) = \binom{n}{i} p^i (1 - p)^{t - i}@f$ where @f$t@f$
4185 * and @f$p@f$ are the parameters of the distribution.
4186 */
4187 template<typename _IntType = int>
4188 class negative_binomial_distribution
4189 {
4190 static_assert(std::is_integral<_IntType>::value,
4191 "result_type must be an integral type");
4192
4193 public:
4194 /** The type of the range of the distribution. */
4195 typedef _IntType result_type;
4196
4197 /** Parameter type. */
4198 struct param_type
4199 {
4200 typedef negative_binomial_distribution<_IntType> distribution_type;
4201
4202 param_type() : param_type(1) { }
4203
4204 explicit
4205 param_type(_IntType __k, double __p = 0.5)
4206 : _M_k(__k), _M_p(__p)
4207 {
4208 __glibcxx_assert((_M_k > 0) && (_M_p > 0.0) && (_M_p <= 1.0));
4209 }
4210
4211 _IntType
4212 k() const
4213 { return _M_k; }
4214
4215 double
4216 p() const
4217 { return _M_p; }
4218
4219 friend bool
4220 operator==(const param_type& __p1, const param_type& __p2)
4221 { return __p1._M_k == __p2._M_k && __p1._M_p == __p2._M_p; }
4222
4223 friend bool
4224 operator!=(const param_type& __p1, const param_type& __p2)
4225 { return !(__p1 == __p2); }
4226
4227 private:
4228 _IntType _M_k;
4229 double _M_p;
4230 };
4231
4232 negative_binomial_distribution() : negative_binomial_distribution(1) { }
4233
4234 explicit
4235 negative_binomial_distribution(_IntType __k, double __p = 0.5)
4236 : _M_param(__k, __p), _M_gd(__k, (1.0 - __p) / __p)
4237 { }
4238
4239 explicit
4240 negative_binomial_distribution(const param_type& __p)
4241 : _M_param(__p), _M_gd(__p.k(), (1.0 - __p.p()) / __p.p())
4242 { }
4243
4244 /**
4245 * @brief Resets the distribution state.
4246 */
4247 void
4248 reset()
4249 { _M_gd.reset(); }
4250
4251 /**
4252 * @brief Return the @f$k@f$ parameter of the distribution.
4253 */
4254 _IntType
4255 k() const
4256 { return _M_param.k(); }
4257
4258 /**
4259 * @brief Return the @f$p@f$ parameter of the distribution.
4260 */
4261 double
4262 p() const
4263 { return _M_param.p(); }
4264
4265 /**
4266 * @brief Returns the parameter set of the distribution.
4267 */
4268 param_type
4269 param() const
4270 { return _M_param; }
4271
4272 /**
4273 * @brief Sets the parameter set of the distribution.
4274 * @param __param The new parameter set of the distribution.
4275 */
4276 void
4277 param(const param_type& __param)
4278 { _M_param = __param; }
4279
4280 /**
4281 * @brief Returns the greatest lower bound value of the distribution.
4282 */
4283 result_type
4284 min() const
4285 { return result_type(0); }
4286
4287 /**
4288 * @brief Returns the least upper bound value of the distribution.
4289 */
4290 result_type
4291 max() const
4292 { return std::numeric_limits<result_type>::max(); }
4293
4294 /**
4295 * @brief Generating functions.
4296 */
4297 template<typename _UniformRandomNumberGenerator>
4298 result_type
4299 operator()(_UniformRandomNumberGenerator& __urng);
4300
4301 template<typename _UniformRandomNumberGenerator>
4302 result_type
4303 operator()(_UniformRandomNumberGenerator& __urng,
4304 const param_type& __p);
4305
4306 template<typename _ForwardIterator,
4307 typename _UniformRandomNumberGenerator>
4308 void
4309 __generate(_ForwardIterator __f, _ForwardIterator __t,
4310 _UniformRandomNumberGenerator& __urng)
4311 { this->__generate_impl(__f, __t, __urng); }
4312
4313 template<typename _ForwardIterator,
4314 typename _UniformRandomNumberGenerator>
4315 void
4316 __generate(_ForwardIterator __f, _ForwardIterator __t,
4317 _UniformRandomNumberGenerator& __urng,
4318 const param_type& __p)
4319 { this->__generate_impl(__f, __t, __urng, __p); }
4320
4321 template<typename _UniformRandomNumberGenerator>
4322 void
4323 __generate(result_type* __f, result_type* __t,
4324 _UniformRandomNumberGenerator& __urng)
4325 { this->__generate_impl(__f, __t, __urng); }
4326
4327 template<typename _UniformRandomNumberGenerator>
4328 void
4329 __generate(result_type* __f, result_type* __t,
4330 _UniformRandomNumberGenerator& __urng,
4331 const param_type& __p)
4332 { this->__generate_impl(__f, __t, __urng, __p); }
4333
4334 /**
4335 * @brief Return true if two negative binomial distributions have
4336 * the same parameters and the sequences that would be
4337 * generated are equal.
4338 */
4339 friend bool
4340 operator==(const negative_binomial_distribution& __d1,
4341 const negative_binomial_distribution& __d2)
4342 { return __d1._M_param == __d2._M_param && __d1._M_gd == __d2._M_gd; }
4343
4344 /**
4345 * @brief Inserts a %negative_binomial_distribution random
4346 * number distribution @p __x into the output stream @p __os.
4347 *
4348 * @param __os An output stream.
4349 * @param __x A %negative_binomial_distribution random number
4350 * distribution.
4351 *
4352 * @returns The output stream with the state of @p __x inserted or in
4353 * an error state.
4354 */
4355 template<typename _IntType1, typename _CharT, typename _Traits>
4356 friend std::basic_ostream<_CharT, _Traits>&
4357 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
4358 const std::negative_binomial_distribution<_IntType1>& __x);
4359
4360 /**
4361 * @brief Extracts a %negative_binomial_distribution random number
4362 * distribution @p __x from the input stream @p __is.
4363 *
4364 * @param __is An input stream.
4365 * @param __x A %negative_binomial_distribution random number
4366 * generator engine.
4367 *
4368 * @returns The input stream with @p __x extracted or in an error state.
4369 */
4370 template<typename _IntType1, typename _CharT, typename _Traits>
4371 friend std::basic_istream<_CharT, _Traits>&
4372 operator>>(std::basic_istream<_CharT, _Traits>& __is,
4373 std::negative_binomial_distribution<_IntType1>& __x);
4374
4375 private:
4376 template<typename _ForwardIterator,
4377 typename _UniformRandomNumberGenerator>
4378 void
4379 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
4380 _UniformRandomNumberGenerator& __urng);
4381 template<typename _ForwardIterator,
4382 typename _UniformRandomNumberGenerator>
4383 void
4384 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
4385 _UniformRandomNumberGenerator& __urng,
4386 const param_type& __p);
4387
4388 param_type _M_param;
4389
4390 std::gamma_distribution<double> _M_gd;
4391 };
4392
4393 /**
4394 * @brief Return true if two negative binomial distributions are different.
4395 */
4396 template<typename _IntType>
4397 inline bool
4398 operator!=(const std::negative_binomial_distribution<_IntType>& __d1,
4399 const std::negative_binomial_distribution<_IntType>& __d2)
4400 { return !(__d1 == __d2); }
4401
4402
4403 /* @} */ // group random_distributions_bernoulli
4404
4405 /**
4406 * @addtogroup random_distributions_poisson Poisson Distributions
4407 * @ingroup random_distributions
4408 * @{
4409 */
4410
4411 /**
4412 * @brief A discrete Poisson random number distribution.
4413 *
4414 * The formula for the Poisson probability density function is
4415 * @f$p(i|\mu) = \frac{\mu^i}{i!} e^{-\mu}@f$ where @f$\mu@f$ is the
4416 * parameter of the distribution.
4417 */
4418 template<typename _IntType = int>
4419 class poisson_distribution
4420 {
4421 static_assert(std::is_integral<_IntType>::value,
4422 "result_type must be an integral type");
4423
4424 public:
4425 /** The type of the range of the distribution. */
4426 typedef _IntType result_type;
4427
4428 /** Parameter type. */
4429 struct param_type
4430 {
4431 typedef poisson_distribution<_IntType> distribution_type;
4432 friend class poisson_distribution<_IntType>;
4433
4434 param_type() : param_type(1.0) { }
4435
4436 explicit
4437 param_type(double __mean)
4438 : _M_mean(__mean)
4439 {
4440 __glibcxx_assert(_M_mean > 0.0);
4441 _M_initialize();
4442 }
4443
4444 double
4445 mean() const
4446 { return _M_mean; }
4447
4448 friend bool
4449 operator==(const param_type& __p1, const param_type& __p2)
4450 { return __p1._M_mean == __p2._M_mean; }
4451
4452 friend bool
4453 operator!=(const param_type& __p1, const param_type& __p2)
4454 { return !(__p1 == __p2); }
4455
4456 private:
4457 // Hosts either log(mean) or the threshold of the simple method.
4458 void
4459 _M_initialize();
4460
4461 double _M_mean;
4462
4463 double _M_lm_thr;
4464 #if _GLIBCXX_USE_C99_MATH_TR1
4465 double _M_lfm, _M_sm, _M_d, _M_scx, _M_1cx, _M_c2b, _M_cb;
4466 #endif
4467 };
4468
4469 // constructors and member functions
4470
4471 poisson_distribution() : poisson_distribution(1.0) { }
4472
4473 explicit
4474 poisson_distribution(double __mean)
4475 : _M_param(__mean), _M_nd()
4476 { }
4477
4478 explicit
4479 poisson_distribution(const param_type& __p)
4480 : _M_param(__p), _M_nd()
4481 { }
4482
4483 /**
4484 * @brief Resets the distribution state.
4485 */
4486 void
4487 reset()
4488 { _M_nd.reset(); }
4489
4490 /**
4491 * @brief Returns the distribution parameter @p mean.
4492 */
4493 double
4494 mean() const
4495 { return _M_param.mean(); }
4496
4497 /**
4498 * @brief Returns the parameter set of the distribution.
4499 */
4500 param_type
4501 param() const
4502 { return _M_param; }
4503
4504 /**
4505 * @brief Sets the parameter set of the distribution.
4506 * @param __param The new parameter set of the distribution.
4507 */
4508 void
4509 param(const param_type& __param)
4510 { _M_param = __param; }
4511
4512 /**
4513 * @brief Returns the greatest lower bound value of the distribution.
4514 */
4515 result_type
4516 min() const
4517 { return 0; }
4518
4519 /**
4520 * @brief Returns the least upper bound value of the distribution.
4521 */
4522 result_type
4523 max() const
4524 { return std::numeric_limits<result_type>::max(); }
4525
4526 /**
4527 * @brief Generating functions.
4528 */
4529 template<typename _UniformRandomNumberGenerator>
4530 result_type
4531 operator()(_UniformRandomNumberGenerator& __urng)
4532 { return this->operator()(__urng, _M_param); }
4533
4534 template<typename _UniformRandomNumberGenerator>
4535 result_type
4536 operator()(_UniformRandomNumberGenerator& __urng,
4537 const param_type& __p);
4538
4539 template<typename _ForwardIterator,
4540 typename _UniformRandomNumberGenerator>
4541 void
4542 __generate(_ForwardIterator __f, _ForwardIterator __t,
4543 _UniformRandomNumberGenerator& __urng)
4544 { this->__generate(__f, __t, __urng, _M_param); }
4545
4546 template<typename _ForwardIterator,
4547 typename _UniformRandomNumberGenerator>
4548 void
4549 __generate(_ForwardIterator __f, _ForwardIterator __t,
4550 _UniformRandomNumberGenerator& __urng,
4551 const param_type& __p)
4552 { this->__generate_impl(__f, __t, __urng, __p); }
4553
4554 template<typename _UniformRandomNumberGenerator>
4555 void
4556 __generate(result_type* __f, result_type* __t,
4557 _UniformRandomNumberGenerator& __urng,
4558 const param_type& __p)
4559 { this->__generate_impl(__f, __t, __urng, __p); }
4560
4561 /**
4562 * @brief Return true if two Poisson distributions have the same
4563 * parameters and the sequences that would be generated
4564 * are equal.
4565 */
4566 friend bool
4567 operator==(const poisson_distribution& __d1,
4568 const poisson_distribution& __d2)
4569 #ifdef _GLIBCXX_USE_C99_MATH_TR1
4570 { return __d1._M_param == __d2._M_param && __d1._M_nd == __d2._M_nd; }
4571 #else
4572 { return __d1._M_param == __d2._M_param; }
4573 #endif
4574
4575 /**
4576 * @brief Inserts a %poisson_distribution random number distribution
4577 * @p __x into the output stream @p __os.
4578 *
4579 * @param __os An output stream.
4580 * @param __x A %poisson_distribution random number distribution.
4581 *
4582 * @returns The output stream with the state of @p __x inserted or in
4583 * an error state.
4584 */
4585 template<typename _IntType1, typename _CharT, typename _Traits>
4586 friend std::basic_ostream<_CharT, _Traits>&
4587 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
4588 const std::poisson_distribution<_IntType1>& __x);
4589
4590 /**
4591 * @brief Extracts a %poisson_distribution random number distribution
4592 * @p __x from the input stream @p __is.
4593 *
4594 * @param __is An input stream.
4595 * @param __x A %poisson_distribution random number generator engine.
4596 *
4597 * @returns The input stream with @p __x extracted or in an error
4598 * state.
4599 */
4600 template<typename _IntType1, typename _CharT, typename _Traits>
4601 friend std::basic_istream<_CharT, _Traits>&
4602 operator>>(std::basic_istream<_CharT, _Traits>& __is,
4603 std::poisson_distribution<_IntType1>& __x);
4604
4605 private:
4606 template<typename _ForwardIterator,
4607 typename _UniformRandomNumberGenerator>
4608 void
4609 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
4610 _UniformRandomNumberGenerator& __urng,
4611 const param_type& __p);
4612
4613 param_type _M_param;
4614
4615 // NB: Unused when _GLIBCXX_USE_C99_MATH_TR1 is undefined.
4616 std::normal_distribution<double> _M_nd;
4617 };
4618
4619 /**
4620 * @brief Return true if two Poisson distributions are different.
4621 */
4622 template<typename _IntType>
4623 inline bool
4624 operator!=(const std::poisson_distribution<_IntType>& __d1,
4625 const std::poisson_distribution<_IntType>& __d2)
4626 { return !(__d1 == __d2); }
4627
4628
4629 /**
4630 * @brief An exponential continuous distribution for random numbers.
4631 *
4632 * The formula for the exponential probability density function is
4633 * @f$p(x|\lambda) = \lambda e^{-\lambda x}@f$.
4634 *
4635 * <table border=1 cellpadding=10 cellspacing=0>
4636 * <caption align=top>Distribution Statistics</caption>
4637 * <tr><td>Mean</td><td>@f$\frac{1}{\lambda}@f$</td></tr>
4638 * <tr><td>Median</td><td>@f$\frac{\ln 2}{\lambda}@f$</td></tr>
4639 * <tr><td>Mode</td><td>@f$zero@f$</td></tr>
4640 * <tr><td>Range</td><td>@f$[0, \infty]@f$</td></tr>
4641 * <tr><td>Standard Deviation</td><td>@f$\frac{1}{\lambda}@f$</td></tr>
4642 * </table>
4643 */
4644 template<typename _RealType = double>
4645 class exponential_distribution
4646 {
4647 static_assert(std::is_floating_point<_RealType>::value,
4648 "result_type must be a floating point type");
4649
4650 public:
4651 /** The type of the range of the distribution. */
4652 typedef _RealType result_type;
4653
4654 /** Parameter type. */
4655 struct param_type
4656 {
4657 typedef exponential_distribution<_RealType> distribution_type;
4658
4659 param_type() : param_type(1.0) { }
4660
4661 explicit
4662 param_type(_RealType __lambda)
4663 : _M_lambda(__lambda)
4664 {
4665 __glibcxx_assert(_M_lambda > _RealType(0));
4666 }
4667
4668 _RealType
4669 lambda() const
4670 { return _M_lambda; }
4671
4672 friend bool
4673 operator==(const param_type& __p1, const param_type& __p2)
4674 { return __p1._M_lambda == __p2._M_lambda; }
4675
4676 friend bool
4677 operator!=(const param_type& __p1, const param_type& __p2)
4678 { return !(__p1 == __p2); }
4679
4680 private:
4681 _RealType _M_lambda;
4682 };
4683
4684 public:
4685 /**
4686 * @brief Constructs an exponential distribution with inverse scale
4687 * parameter 1.0
4688 */
4689 exponential_distribution() : exponential_distribution(1.0) { }
4690
4691 /**
4692 * @brief Constructs an exponential distribution with inverse scale
4693 * parameter @f$\lambda@f$.
4694 */
4695 explicit
4696 exponential_distribution(_RealType __lambda)
4697 : _M_param(__lambda)
4698 { }
4699
4700 explicit
4701 exponential_distribution(const param_type& __p)
4702 : _M_param(__p)
4703 { }
4704
4705 /**
4706 * @brief Resets the distribution state.
4707 *
4708 * Has no effect on exponential distributions.
4709 */
4710 void
4711 reset() { }
4712
4713 /**
4714 * @brief Returns the inverse scale parameter of the distribution.
4715 */
4716 _RealType
4717 lambda() const
4718 { return _M_param.lambda(); }
4719
4720 /**
4721 * @brief Returns the parameter set of the distribution.
4722 */
4723 param_type
4724 param() const
4725 { return _M_param; }
4726
4727 /**
4728 * @brief Sets the parameter set of the distribution.
4729 * @param __param The new parameter set of the distribution.
4730 */
4731 void
4732 param(const param_type& __param)
4733 { _M_param = __param; }
4734
4735 /**
4736 * @brief Returns the greatest lower bound value of the distribution.
4737 */
4738 result_type
4739 min() const
4740 { return result_type(0); }
4741
4742 /**
4743 * @brief Returns the least upper bound value of the distribution.
4744 */
4745 result_type
4746 max() const
4747 { return std::numeric_limits<result_type>::max(); }
4748
4749 /**
4750 * @brief Generating functions.
4751 */
4752 template<typename _UniformRandomNumberGenerator>
4753 result_type
4754 operator()(_UniformRandomNumberGenerator& __urng)
4755 { return this->operator()(__urng, _M_param); }
4756
4757 template<typename _UniformRandomNumberGenerator>
4758 result_type
4759 operator()(_UniformRandomNumberGenerator& __urng,
4760 const param_type& __p)
4761 {
4762 __detail::_Adaptor<_UniformRandomNumberGenerator, result_type>
4763 __aurng(__urng);
4764 return -std::log(result_type(1) - __aurng()) / __p.lambda();
4765 }
4766
4767 template<typename _ForwardIterator,
4768 typename _UniformRandomNumberGenerator>
4769 void
4770 __generate(_ForwardIterator __f, _ForwardIterator __t,
4771 _UniformRandomNumberGenerator& __urng)
4772 { this->__generate(__f, __t, __urng, _M_param); }
4773
4774 template<typename _ForwardIterator,
4775 typename _UniformRandomNumberGenerator>
4776 void
4777 __generate(_ForwardIterator __f, _ForwardIterator __t,
4778 _UniformRandomNumberGenerator& __urng,
4779 const param_type& __p)
4780 { this->__generate_impl(__f, __t, __urng, __p); }
4781
4782 template<typename _UniformRandomNumberGenerator>
4783 void
4784 __generate(result_type* __f, result_type* __t,
4785 _UniformRandomNumberGenerator& __urng,
4786 const param_type& __p)
4787 { this->__generate_impl(__f, __t, __urng, __p); }
4788
4789 /**
4790 * @brief Return true if two exponential distributions have the same
4791 * parameters.
4792 */
4793 friend bool
4794 operator==(const exponential_distribution& __d1,
4795 const exponential_distribution& __d2)
4796 { return __d1._M_param == __d2._M_param; }
4797
4798 private:
4799 template<typename _ForwardIterator,
4800 typename _UniformRandomNumberGenerator>
4801 void
4802 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
4803 _UniformRandomNumberGenerator& __urng,
4804 const param_type& __p);
4805
4806 param_type _M_param;
4807 };
4808
4809 /**
4810 * @brief Return true if two exponential distributions have different
4811 * parameters.
4812 */
4813 template<typename _RealType>
4814 inline bool
4815 operator!=(const std::exponential_distribution<_RealType>& __d1,
4816 const std::exponential_distribution<_RealType>& __d2)
4817 { return !(__d1 == __d2); }
4818
4819 /**
4820 * @brief Inserts a %exponential_distribution random number distribution
4821 * @p __x into the output stream @p __os.
4822 *
4823 * @param __os An output stream.
4824 * @param __x A %exponential_distribution random number distribution.
4825 *
4826 * @returns The output stream with the state of @p __x inserted or in
4827 * an error state.
4828 */
4829 template<typename _RealType, typename _CharT, typename _Traits>
4830 std::basic_ostream<_CharT, _Traits>&
4831 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
4832 const std::exponential_distribution<_RealType>& __x);
4833
4834 /**
4835 * @brief Extracts a %exponential_distribution random number distribution
4836 * @p __x from the input stream @p __is.
4837 *
4838 * @param __is An input stream.
4839 * @param __x A %exponential_distribution random number
4840 * generator engine.
4841 *
4842 * @returns The input stream with @p __x extracted or in an error state.
4843 */
4844 template<typename _RealType, typename _CharT, typename _Traits>
4845 std::basic_istream<_CharT, _Traits>&
4846 operator>>(std::basic_istream<_CharT, _Traits>& __is,
4847 std::exponential_distribution<_RealType>& __x);
4848
4849
4850 /**
4851 * @brief A weibull_distribution random number distribution.
4852 *
4853 * The formula for the normal probability density function is:
4854 * @f[
4855 * p(x|\alpha,\beta) = \frac{\alpha}{\beta} (\frac{x}{\beta})^{\alpha-1}
4856 * \exp{(-(\frac{x}{\beta})^\alpha)}
4857 * @f]
4858 */
4859 template<typename _RealType = double>
4860 class weibull_distribution
4861 {
4862 static_assert(std::is_floating_point<_RealType>::value,
4863 "result_type must be a floating point type");
4864
4865 public:
4866 /** The type of the range of the distribution. */
4867 typedef _RealType result_type;
4868
4869 /** Parameter type. */
4870 struct param_type
4871 {
4872 typedef weibull_distribution<_RealType> distribution_type;
4873
4874 param_type() : param_type(1.0) { }
4875
4876 explicit
4877 param_type(_RealType __a, _RealType __b = _RealType(1.0))
4878 : _M_a(__a), _M_b(__b)
4879 { }
4880
4881 _RealType
4882 a() const
4883 { return _M_a; }
4884
4885 _RealType
4886 b() const
4887 { return _M_b; }
4888
4889 friend bool
4890 operator==(const param_type& __p1, const param_type& __p2)
4891 { return __p1._M_a == __p2._M_a && __p1._M_b == __p2._M_b; }
4892
4893 friend bool
4894 operator!=(const param_type& __p1, const param_type& __p2)
4895 { return !(__p1 == __p2); }
4896
4897 private:
4898 _RealType _M_a;
4899 _RealType _M_b;
4900 };
4901
4902 weibull_distribution() : weibull_distribution(1.0) { }
4903
4904 explicit
4905 weibull_distribution(_RealType __a, _RealType __b = _RealType(1))
4906 : _M_param(__a, __b)
4907 { }
4908
4909 explicit
4910 weibull_distribution(const param_type& __p)
4911 : _M_param(__p)
4912 { }
4913
4914 /**
4915 * @brief Resets the distribution state.
4916 */
4917 void
4918 reset()
4919 { }
4920
4921 /**
4922 * @brief Return the @f$a@f$ parameter of the distribution.
4923 */
4924 _RealType
4925 a() const
4926 { return _M_param.a(); }
4927
4928 /**
4929 * @brief Return the @f$b@f$ parameter of the distribution.
4930 */
4931 _RealType
4932 b() const
4933 { return _M_param.b(); }
4934
4935 /**
4936 * @brief Returns the parameter set of the distribution.
4937 */
4938 param_type
4939 param() const
4940 { return _M_param; }
4941
4942 /**
4943 * @brief Sets the parameter set of the distribution.
4944 * @param __param The new parameter set of the distribution.
4945 */
4946 void
4947 param(const param_type& __param)
4948 { _M_param = __param; }
4949
4950 /**
4951 * @brief Returns the greatest lower bound value of the distribution.
4952 */
4953 result_type
4954 min() const
4955 { return result_type(0); }
4956
4957 /**
4958 * @brief Returns the least upper bound value of the distribution.
4959 */
4960 result_type
4961 max() const
4962 { return std::numeric_limits<result_type>::max(); }
4963
4964 /**
4965 * @brief Generating functions.
4966 */
4967 template<typename _UniformRandomNumberGenerator>
4968 result_type
4969 operator()(_UniformRandomNumberGenerator& __urng)
4970 { return this->operator()(__urng, _M_param); }
4971
4972 template<typename _UniformRandomNumberGenerator>
4973 result_type
4974 operator()(_UniformRandomNumberGenerator& __urng,
4975 const param_type& __p);
4976
4977 template<typename _ForwardIterator,
4978 typename _UniformRandomNumberGenerator>
4979 void
4980 __generate(_ForwardIterator __f, _ForwardIterator __t,
4981 _UniformRandomNumberGenerator& __urng)
4982 { this->__generate(__f, __t, __urng, _M_param); }
4983
4984 template<typename _ForwardIterator,
4985 typename _UniformRandomNumberGenerator>
4986 void
4987 __generate(_ForwardIterator __f, _ForwardIterator __t,
4988 _UniformRandomNumberGenerator& __urng,
4989 const param_type& __p)
4990 { this->__generate_impl(__f, __t, __urng, __p); }
4991
4992 template<typename _UniformRandomNumberGenerator>
4993 void
4994 __generate(result_type* __f, result_type* __t,
4995 _UniformRandomNumberGenerator& __urng,
4996 const param_type& __p)
4997 { this->__generate_impl(__f, __t, __urng, __p); }
4998
4999 /**
5000 * @brief Return true if two Weibull distributions have the same
5001 * parameters.
5002 */
5003 friend bool
5004 operator==(const weibull_distribution& __d1,
5005 const weibull_distribution& __d2)
5006 { return __d1._M_param == __d2._M_param; }
5007
5008 private:
5009 template<typename _ForwardIterator,
5010 typename _UniformRandomNumberGenerator>
5011 void
5012 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
5013 _UniformRandomNumberGenerator& __urng,
5014 const param_type& __p);
5015
5016 param_type _M_param;
5017 };
5018
5019 /**
5020 * @brief Return true if two Weibull distributions have different
5021 * parameters.
5022 */
5023 template<typename _RealType>
5024 inline bool
5025 operator!=(const std::weibull_distribution<_RealType>& __d1,
5026 const std::weibull_distribution<_RealType>& __d2)
5027 { return !(__d1 == __d2); }
5028
5029 /**
5030 * @brief Inserts a %weibull_distribution random number distribution
5031 * @p __x into the output stream @p __os.
5032 *
5033 * @param __os An output stream.
5034 * @param __x A %weibull_distribution random number distribution.
5035 *
5036 * @returns The output stream with the state of @p __x inserted or in
5037 * an error state.
5038 */
5039 template<typename _RealType, typename _CharT, typename _Traits>
5040 std::basic_ostream<_CharT, _Traits>&
5041 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
5042 const std::weibull_distribution<_RealType>& __x);
5043
5044 /**
5045 * @brief Extracts a %weibull_distribution random number distribution
5046 * @p __x from the input stream @p __is.
5047 *
5048 * @param __is An input stream.
5049 * @param __x A %weibull_distribution random number
5050 * generator engine.
5051 *
5052 * @returns The input stream with @p __x extracted or in an error state.
5053 */
5054 template<typename _RealType, typename _CharT, typename _Traits>
5055 std::basic_istream<_CharT, _Traits>&
5056 operator>>(std::basic_istream<_CharT, _Traits>& __is,
5057 std::weibull_distribution<_RealType>& __x);
5058
5059
5060 /**
5061 * @brief A extreme_value_distribution random number distribution.
5062 *
5063 * The formula for the normal probability mass function is
5064 * @f[
5065 * p(x|a,b) = \frac{1}{b}
5066 * \exp( \frac{a-x}{b} - \exp(\frac{a-x}{b}))
5067 * @f]
5068 */
5069 template<typename _RealType = double>
5070 class extreme_value_distribution
5071 {
5072 static_assert(std::is_floating_point<_RealType>::value,
5073 "result_type must be a floating point type");
5074
5075 public:
5076 /** The type of the range of the distribution. */
5077 typedef _RealType result_type;
5078
5079 /** Parameter type. */
5080 struct param_type
5081 {
5082 typedef extreme_value_distribution<_RealType> distribution_type;
5083
5084 param_type() : param_type(0.0) { }
5085
5086 explicit
5087 param_type(_RealType __a, _RealType __b = _RealType(1.0))
5088 : _M_a(__a), _M_b(__b)
5089 { }
5090
5091 _RealType
5092 a() const
5093 { return _M_a; }
5094
5095 _RealType
5096 b() const
5097 { return _M_b; }
5098
5099 friend bool
5100 operator==(const param_type& __p1, const param_type& __p2)
5101 { return __p1._M_a == __p2._M_a && __p1._M_b == __p2._M_b; }
5102
5103 friend bool
5104 operator!=(const param_type& __p1, const param_type& __p2)
5105 { return !(__p1 == __p2); }
5106
5107 private:
5108 _RealType _M_a;
5109 _RealType _M_b;
5110 };
5111
5112 extreme_value_distribution() : extreme_value_distribution(0.0) { }
5113
5114 explicit
5115 extreme_value_distribution(_RealType __a, _RealType __b = _RealType(1))
5116 : _M_param(__a, __b)
5117 { }
5118
5119 explicit
5120 extreme_value_distribution(const param_type& __p)
5121 : _M_param(__p)
5122 { }
5123
5124 /**
5125 * @brief Resets the distribution state.
5126 */
5127 void
5128 reset()
5129 { }
5130
5131 /**
5132 * @brief Return the @f$a@f$ parameter of the distribution.
5133 */
5134 _RealType
5135 a() const
5136 { return _M_param.a(); }
5137
5138 /**
5139 * @brief Return the @f$b@f$ parameter of the distribution.
5140 */
5141 _RealType
5142 b() const
5143 { return _M_param.b(); }
5144
5145 /**
5146 * @brief Returns the parameter set of the distribution.
5147 */
5148 param_type
5149 param() const
5150 { return _M_param; }
5151
5152 /**
5153 * @brief Sets the parameter set of the distribution.
5154 * @param __param The new parameter set of the distribution.
5155 */
5156 void
5157 param(const param_type& __param)
5158 { _M_param = __param; }
5159
5160 /**
5161 * @brief Returns the greatest lower bound value of the distribution.
5162 */
5163 result_type
5164 min() const
5165 { return std::numeric_limits<result_type>::lowest(); }
5166
5167 /**
5168 * @brief Returns the least upper bound value of the distribution.
5169 */
5170 result_type
5171 max() const
5172 { return std::numeric_limits<result_type>::max(); }
5173
5174 /**
5175 * @brief Generating functions.
5176 */
5177 template<typename _UniformRandomNumberGenerator>
5178 result_type
5179 operator()(_UniformRandomNumberGenerator& __urng)
5180 { return this->operator()(__urng, _M_param); }
5181
5182 template<typename _UniformRandomNumberGenerator>
5183 result_type
5184 operator()(_UniformRandomNumberGenerator& __urng,
5185 const param_type& __p);
5186
5187 template<typename _ForwardIterator,
5188 typename _UniformRandomNumberGenerator>
5189 void
5190 __generate(_ForwardIterator __f, _ForwardIterator __t,
5191 _UniformRandomNumberGenerator& __urng)
5192 { this->__generate(__f, __t, __urng, _M_param); }
5193
5194 template<typename _ForwardIterator,
5195 typename _UniformRandomNumberGenerator>
5196 void
5197 __generate(_ForwardIterator __f, _ForwardIterator __t,
5198 _UniformRandomNumberGenerator& __urng,
5199 const param_type& __p)
5200 { this->__generate_impl(__f, __t, __urng, __p); }
5201
5202 template<typename _UniformRandomNumberGenerator>
5203 void
5204 __generate(result_type* __f, result_type* __t,
5205 _UniformRandomNumberGenerator& __urng,
5206 const param_type& __p)
5207 { this->__generate_impl(__f, __t, __urng, __p); }
5208
5209 /**
5210 * @brief Return true if two extreme value distributions have the same
5211 * parameters.
5212 */
5213 friend bool
5214 operator==(const extreme_value_distribution& __d1,
5215 const extreme_value_distribution& __d2)
5216 { return __d1._M_param == __d2._M_param; }
5217
5218 private:
5219 template<typename _ForwardIterator,
5220 typename _UniformRandomNumberGenerator>
5221 void
5222 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
5223 _UniformRandomNumberGenerator& __urng,
5224 const param_type& __p);
5225
5226 param_type _M_param;
5227 };
5228
5229 /**
5230 * @brief Return true if two extreme value distributions have different
5231 * parameters.
5232 */
5233 template<typename _RealType>
5234 inline bool
5235 operator!=(const std::extreme_value_distribution<_RealType>& __d1,
5236 const std::extreme_value_distribution<_RealType>& __d2)
5237 { return !(__d1 == __d2); }
5238
5239 /**
5240 * @brief Inserts a %extreme_value_distribution random number distribution
5241 * @p __x into the output stream @p __os.
5242 *
5243 * @param __os An output stream.
5244 * @param __x A %extreme_value_distribution random number distribution.
5245 *
5246 * @returns The output stream with the state of @p __x inserted or in
5247 * an error state.
5248 */
5249 template<typename _RealType, typename _CharT, typename _Traits>
5250 std::basic_ostream<_CharT, _Traits>&
5251 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
5252 const std::extreme_value_distribution<_RealType>& __x);
5253
5254 /**
5255 * @brief Extracts a %extreme_value_distribution random number
5256 * distribution @p __x from the input stream @p __is.
5257 *
5258 * @param __is An input stream.
5259 * @param __x A %extreme_value_distribution random number
5260 * generator engine.
5261 *
5262 * @returns The input stream with @p __x extracted or in an error state.
5263 */
5264 template<typename _RealType, typename _CharT, typename _Traits>
5265 std::basic_istream<_CharT, _Traits>&
5266 operator>>(std::basic_istream<_CharT, _Traits>& __is,
5267 std::extreme_value_distribution<_RealType>& __x);
5268
5269
5270 /**
5271 * @brief A discrete_distribution random number distribution.
5272 *
5273 * The formula for the discrete probability mass function is
5274 *
5275 */
5276 template<typename _IntType = int>
5277 class discrete_distribution
5278 {
5279 static_assert(std::is_integral<_IntType>::value,
5280 "result_type must be an integral type");
5281
5282 public:
5283 /** The type of the range of the distribution. */
5284 typedef _IntType result_type;
5285
5286 /** Parameter type. */
5287 struct param_type
5288 {
5289 typedef discrete_distribution<_IntType> distribution_type;
5290 friend class discrete_distribution<_IntType>;
5291
5292 param_type()
5293 : _M_prob(), _M_cp()
5294 { }
5295
5296 template<typename _InputIterator>
5297 param_type(_InputIterator __wbegin,
5298 _InputIterator __wend)
5299 : _M_prob(__wbegin, __wend), _M_cp()
5300 { _M_initialize(); }
5301
5302 param_type(initializer_list<double> __wil)
5303 : _M_prob(__wil.begin(), __wil.end()), _M_cp()
5304 { _M_initialize(); }
5305
5306 template<typename _Func>
5307 param_type(size_t __nw, double __xmin, double __xmax,
5308 _Func __fw);
5309
5310 // See: http://cpp-next.com/archive/2010/10/implicit-move-must-go/
5311 param_type(const param_type&) = default;
5312 param_type& operator=(const param_type&) = default;
5313
5314 std::vector<double>
5315 probabilities() const
5316 { return _M_prob.empty() ? std::vector<double>(1, 1.0) : _M_prob; }
5317
5318 friend bool
5319 operator==(const param_type& __p1, const param_type& __p2)
5320 { return __p1._M_prob == __p2._M_prob; }
5321
5322 friend bool
5323 operator!=(const param_type& __p1, const param_type& __p2)
5324 { return !(__p1 == __p2); }
5325
5326 private:
5327 void
5328 _M_initialize();
5329
5330 std::vector<double> _M_prob;
5331 std::vector<double> _M_cp;
5332 };
5333
5334 discrete_distribution()
5335 : _M_param()
5336 { }
5337
5338 template<typename _InputIterator>
5339 discrete_distribution(_InputIterator __wbegin,
5340 _InputIterator __wend)
5341 : _M_param(__wbegin, __wend)
5342 { }
5343
5344 discrete_distribution(initializer_list<double> __wl)
5345 : _M_param(__wl)
5346 { }
5347
5348 template<typename _Func>
5349 discrete_distribution(size_t __nw, double __xmin, double __xmax,
5350 _Func __fw)
5351 : _M_param(__nw, __xmin, __xmax, __fw)
5352 { }
5353
5354 explicit
5355 discrete_distribution(const param_type& __p)
5356 : _M_param(__p)
5357 { }
5358
5359 /**
5360 * @brief Resets the distribution state.
5361 */
5362 void
5363 reset()
5364 { }
5365
5366 /**
5367 * @brief Returns the probabilities of the distribution.
5368 */
5369 std::vector<double>
5370 probabilities() const
5371 {
5372 return _M_param._M_prob.empty()
5373 ? std::vector<double>(1, 1.0) : _M_param._M_prob;
5374 }
5375
5376 /**
5377 * @brief Returns the parameter set of the distribution.
5378 */
5379 param_type
5380 param() const
5381 { return _M_param; }
5382
5383 /**
5384 * @brief Sets the parameter set of the distribution.
5385 * @param __param The new parameter set of the distribution.
5386 */
5387 void
5388 param(const param_type& __param)
5389 { _M_param = __param; }
5390
5391 /**
5392 * @brief Returns the greatest lower bound value of the distribution.
5393 */
5394 result_type
5395 min() const
5396 { return result_type(0); }
5397
5398 /**
5399 * @brief Returns the least upper bound value of the distribution.
5400 */
5401 result_type
5402 max() const
5403 {
5404 return _M_param._M_prob.empty()
5405 ? result_type(0) : result_type(_M_param._M_prob.size() - 1);
5406 }
5407
5408 /**
5409 * @brief Generating functions.
5410 */
5411 template<typename _UniformRandomNumberGenerator>
5412 result_type
5413 operator()(_UniformRandomNumberGenerator& __urng)
5414 { return this->operator()(__urng, _M_param); }
5415
5416 template<typename _UniformRandomNumberGenerator>
5417 result_type
5418 operator()(_UniformRandomNumberGenerator& __urng,
5419 const param_type& __p);
5420
5421 template<typename _ForwardIterator,
5422 typename _UniformRandomNumberGenerator>
5423 void
5424 __generate(_ForwardIterator __f, _ForwardIterator __t,
5425 _UniformRandomNumberGenerator& __urng)
5426 { this->__generate(__f, __t, __urng, _M_param); }
5427
5428 template<typename _ForwardIterator,
5429 typename _UniformRandomNumberGenerator>
5430 void
5431 __generate(_ForwardIterator __f, _ForwardIterator __t,
5432 _UniformRandomNumberGenerator& __urng,
5433 const param_type& __p)
5434 { this->__generate_impl(__f, __t, __urng, __p); }
5435
5436 template<typename _UniformRandomNumberGenerator>
5437 void
5438 __generate(result_type* __f, result_type* __t,
5439 _UniformRandomNumberGenerator& __urng,
5440 const param_type& __p)
5441 { this->__generate_impl(__f, __t, __urng, __p); }
5442
5443 /**
5444 * @brief Return true if two discrete distributions have the same
5445 * parameters.
5446 */
5447 friend bool
5448 operator==(const discrete_distribution& __d1,
5449 const discrete_distribution& __d2)
5450 { return __d1._M_param == __d2._M_param; }
5451
5452 /**
5453 * @brief Inserts a %discrete_distribution random number distribution
5454 * @p __x into the output stream @p __os.
5455 *
5456 * @param __os An output stream.
5457 * @param __x A %discrete_distribution random number distribution.
5458 *
5459 * @returns The output stream with the state of @p __x inserted or in
5460 * an error state.
5461 */
5462 template<typename _IntType1, typename _CharT, typename _Traits>
5463 friend std::basic_ostream<_CharT, _Traits>&
5464 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
5465 const std::discrete_distribution<_IntType1>& __x);
5466
5467 /**
5468 * @brief Extracts a %discrete_distribution random number distribution
5469 * @p __x from the input stream @p __is.
5470 *
5471 * @param __is An input stream.
5472 * @param __x A %discrete_distribution random number
5473 * generator engine.
5474 *
5475 * @returns The input stream with @p __x extracted or in an error
5476 * state.
5477 */
5478 template<typename _IntType1, typename _CharT, typename _Traits>
5479 friend std::basic_istream<_CharT, _Traits>&
5480 operator>>(std::basic_istream<_CharT, _Traits>& __is,
5481 std::discrete_distribution<_IntType1>& __x);
5482
5483 private:
5484 template<typename _ForwardIterator,
5485 typename _UniformRandomNumberGenerator>
5486 void
5487 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
5488 _UniformRandomNumberGenerator& __urng,
5489 const param_type& __p);
5490
5491 param_type _M_param;
5492 };
5493
5494 /**
5495 * @brief Return true if two discrete distributions have different
5496 * parameters.
5497 */
5498 template<typename _IntType>
5499 inline bool
5500 operator!=(const std::discrete_distribution<_IntType>& __d1,
5501 const std::discrete_distribution<_IntType>& __d2)
5502 { return !(__d1 == __d2); }
5503
5504
5505 /**
5506 * @brief A piecewise_constant_distribution random number distribution.
5507 *
5508 * The formula for the piecewise constant probability mass function is
5509 *
5510 */
5511 template<typename _RealType = double>
5512 class piecewise_constant_distribution
5513 {
5514 static_assert(std::is_floating_point<_RealType>::value,
5515 "result_type must be a floating point type");
5516
5517 public:
5518 /** The type of the range of the distribution. */
5519 typedef _RealType result_type;
5520
5521 /** Parameter type. */
5522 struct param_type
5523 {
5524 typedef piecewise_constant_distribution<_RealType> distribution_type;
5525 friend class piecewise_constant_distribution<_RealType>;
5526
5527 param_type()
5528 : _M_int(), _M_den(), _M_cp()
5529 { }
5530
5531 template<typename _InputIteratorB, typename _InputIteratorW>
5532 param_type(_InputIteratorB __bfirst,
5533 _InputIteratorB __bend,
5534 _InputIteratorW __wbegin);
5535
5536 template<typename _Func>
5537 param_type(initializer_list<_RealType> __bi, _Func __fw);
5538
5539 template<typename _Func>
5540 param_type(size_t __nw, _RealType __xmin, _RealType __xmax,
5541 _Func __fw);
5542
5543 // See: http://cpp-next.com/archive/2010/10/implicit-move-must-go/
5544 param_type(const param_type&) = default;
5545 param_type& operator=(const param_type&) = default;
5546
5547 std::vector<_RealType>
5548 intervals() const
5549 {
5550 if (_M_int.empty())
5551 {
5552 std::vector<_RealType> __tmp(2);
5553 __tmp[1] = _RealType(1);
5554 return __tmp;
5555 }
5556 else
5557 return _M_int;
5558 }
5559
5560 std::vector<double>
5561 densities() const
5562 { return _M_den.empty() ? std::vector<double>(1, 1.0) : _M_den; }
5563
5564 friend bool
5565 operator==(const param_type& __p1, const param_type& __p2)
5566 { return __p1._M_int == __p2._M_int && __p1._M_den == __p2._M_den; }
5567
5568 friend bool
5569 operator!=(const param_type& __p1, const param_type& __p2)
5570 { return !(__p1 == __p2); }
5571
5572 private:
5573 void
5574 _M_initialize();
5575
5576 std::vector<_RealType> _M_int;
5577 std::vector<double> _M_den;
5578 std::vector<double> _M_cp;
5579 };
5580
5581 piecewise_constant_distribution()
5582 : _M_param()
5583 { }
5584
5585 template<typename _InputIteratorB, typename _InputIteratorW>
5586 piecewise_constant_distribution(_InputIteratorB __bfirst,
5587 _InputIteratorB __bend,
5588 _InputIteratorW __wbegin)
5589 : _M_param(__bfirst, __bend, __wbegin)
5590 { }
5591
5592 template<typename _Func>
5593 piecewise_constant_distribution(initializer_list<_RealType> __bl,
5594 _Func __fw)
5595 : _M_param(__bl, __fw)
5596 { }
5597
5598 template<typename _Func>
5599 piecewise_constant_distribution(size_t __nw,
5600 _RealType __xmin, _RealType __xmax,
5601 _Func __fw)
5602 : _M_param(__nw, __xmin, __xmax, __fw)
5603 { }
5604
5605 explicit
5606 piecewise_constant_distribution(const param_type& __p)
5607 : _M_param(__p)
5608 { }
5609
5610 /**
5611 * @brief Resets the distribution state.
5612 */
5613 void
5614 reset()
5615 { }
5616
5617 /**
5618 * @brief Returns a vector of the intervals.
5619 */
5620 std::vector<_RealType>
5621 intervals() const
5622 {
5623 if (_M_param._M_int.empty())
5624 {
5625 std::vector<_RealType> __tmp(2);
5626 __tmp[1] = _RealType(1);
5627 return __tmp;
5628 }
5629 else
5630 return _M_param._M_int;
5631 }
5632
5633 /**
5634 * @brief Returns a vector of the probability densities.
5635 */
5636 std::vector<double>
5637 densities() const
5638 {
5639 return _M_param._M_den.empty()
5640 ? std::vector<double>(1, 1.0) : _M_param._M_den;
5641 }
5642
5643 /**
5644 * @brief Returns the parameter set of the distribution.
5645 */
5646 param_type
5647 param() const
5648 { return _M_param; }
5649
5650 /**
5651 * @brief Sets the parameter set of the distribution.
5652 * @param __param The new parameter set of the distribution.
5653 */
5654 void
5655 param(const param_type& __param)
5656 { _M_param = __param; }
5657
5658 /**
5659 * @brief Returns the greatest lower bound value of the distribution.
5660 */
5661 result_type
5662 min() const
5663 {
5664 return _M_param._M_int.empty()
5665 ? result_type(0) : _M_param._M_int.front();
5666 }
5667
5668 /**
5669 * @brief Returns the least upper bound value of the distribution.
5670 */
5671 result_type
5672 max() const
5673 {
5674 return _M_param._M_int.empty()
5675 ? result_type(1) : _M_param._M_int.back();
5676 }
5677
5678 /**
5679 * @brief Generating functions.
5680 */
5681 template<typename _UniformRandomNumberGenerator>
5682 result_type
5683 operator()(_UniformRandomNumberGenerator& __urng)
5684 { return this->operator()(__urng, _M_param); }
5685
5686 template<typename _UniformRandomNumberGenerator>
5687 result_type
5688 operator()(_UniformRandomNumberGenerator& __urng,
5689 const param_type& __p);
5690
5691 template<typename _ForwardIterator,
5692 typename _UniformRandomNumberGenerator>
5693 void
5694 __generate(_ForwardIterator __f, _ForwardIterator __t,
5695 _UniformRandomNumberGenerator& __urng)
5696 { this->__generate(__f, __t, __urng, _M_param); }
5697
5698 template<typename _ForwardIterator,
5699 typename _UniformRandomNumberGenerator>
5700 void
5701 __generate(_ForwardIterator __f, _ForwardIterator __t,
5702 _UniformRandomNumberGenerator& __urng,
5703 const param_type& __p)
5704 { this->__generate_impl(__f, __t, __urng, __p); }
5705
5706 template<typename _UniformRandomNumberGenerator>
5707 void
5708 __generate(result_type* __f, result_type* __t,
5709 _UniformRandomNumberGenerator& __urng,
5710 const param_type& __p)
5711 { this->__generate_impl(__f, __t, __urng, __p); }
5712
5713 /**
5714 * @brief Return true if two piecewise constant distributions have the
5715 * same parameters.
5716 */
5717 friend bool
5718 operator==(const piecewise_constant_distribution& __d1,
5719 const piecewise_constant_distribution& __d2)
5720 { return __d1._M_param == __d2._M_param; }
5721
5722 /**
5723 * @brief Inserts a %piecewise_constant_distribution random
5724 * number distribution @p __x into the output stream @p __os.
5725 *
5726 * @param __os An output stream.
5727 * @param __x A %piecewise_constant_distribution random number
5728 * distribution.
5729 *
5730 * @returns The output stream with the state of @p __x inserted or in
5731 * an error state.
5732 */
5733 template<typename _RealType1, typename _CharT, typename _Traits>
5734 friend std::basic_ostream<_CharT, _Traits>&
5735 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
5736 const std::piecewise_constant_distribution<_RealType1>& __x);
5737
5738 /**
5739 * @brief Extracts a %piecewise_constant_distribution random
5740 * number distribution @p __x from the input stream @p __is.
5741 *
5742 * @param __is An input stream.
5743 * @param __x A %piecewise_constant_distribution random number
5744 * generator engine.
5745 *
5746 * @returns The input stream with @p __x extracted or in an error
5747 * state.
5748 */
5749 template<typename _RealType1, typename _CharT, typename _Traits>
5750 friend std::basic_istream<_CharT, _Traits>&
5751 operator>>(std::basic_istream<_CharT, _Traits>& __is,
5752 std::piecewise_constant_distribution<_RealType1>& __x);
5753
5754 private:
5755 template<typename _ForwardIterator,
5756 typename _UniformRandomNumberGenerator>
5757 void
5758 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
5759 _UniformRandomNumberGenerator& __urng,
5760 const param_type& __p);
5761
5762 param_type _M_param;
5763 };
5764
5765 /**
5766 * @brief Return true if two piecewise constant distributions have
5767 * different parameters.
5768 */
5769 template<typename _RealType>
5770 inline bool
5771 operator!=(const std::piecewise_constant_distribution<_RealType>& __d1,
5772 const std::piecewise_constant_distribution<_RealType>& __d2)
5773 { return !(__d1 == __d2); }
5774
5775
5776 /**
5777 * @brief A piecewise_linear_distribution random number distribution.
5778 *
5779 * The formula for the piecewise linear probability mass function is
5780 *
5781 */
5782 template<typename _RealType = double>
5783 class piecewise_linear_distribution
5784 {
5785 static_assert(std::is_floating_point<_RealType>::value,
5786 "result_type must be a floating point type");
5787
5788 public:
5789 /** The type of the range of the distribution. */
5790 typedef _RealType result_type;
5791
5792 /** Parameter type. */
5793 struct param_type
5794 {
5795 typedef piecewise_linear_distribution<_RealType> distribution_type;
5796 friend class piecewise_linear_distribution<_RealType>;
5797
5798 param_type()
5799 : _M_int(), _M_den(), _M_cp(), _M_m()
5800 { }
5801
5802 template<typename _InputIteratorB, typename _InputIteratorW>
5803 param_type(_InputIteratorB __bfirst,
5804 _InputIteratorB __bend,
5805 _InputIteratorW __wbegin);
5806
5807 template<typename _Func>
5808 param_type(initializer_list<_RealType> __bl, _Func __fw);
5809
5810 template<typename _Func>
5811 param_type(size_t __nw, _RealType __xmin, _RealType __xmax,
5812 _Func __fw);
5813
5814 // See: http://cpp-next.com/archive/2010/10/implicit-move-must-go/
5815 param_type(const param_type&) = default;
5816 param_type& operator=(const param_type&) = default;
5817
5818 std::vector<_RealType>
5819 intervals() const
5820 {
5821 if (_M_int.empty())
5822 {
5823 std::vector<_RealType> __tmp(2);
5824 __tmp[1] = _RealType(1);
5825 return __tmp;
5826 }
5827 else
5828 return _M_int;
5829 }
5830
5831 std::vector<double>
5832 densities() const
5833 { return _M_den.empty() ? std::vector<double>(2, 1.0) : _M_den; }
5834
5835 friend bool
5836 operator==(const param_type& __p1, const param_type& __p2)
5837 { return __p1._M_int == __p2._M_int && __p1._M_den == __p2._M_den; }
5838
5839 friend bool
5840 operator!=(const param_type& __p1, const param_type& __p2)
5841 { return !(__p1 == __p2); }
5842
5843 private:
5844 void
5845 _M_initialize();
5846
5847 std::vector<_RealType> _M_int;
5848 std::vector<double> _M_den;
5849 std::vector<double> _M_cp;
5850 std::vector<double> _M_m;
5851 };
5852
5853 piecewise_linear_distribution()
5854 : _M_param()
5855 { }
5856
5857 template<typename _InputIteratorB, typename _InputIteratorW>
5858 piecewise_linear_distribution(_InputIteratorB __bfirst,
5859 _InputIteratorB __bend,
5860 _InputIteratorW __wbegin)
5861 : _M_param(__bfirst, __bend, __wbegin)
5862 { }
5863
5864 template<typename _Func>
5865 piecewise_linear_distribution(initializer_list<_RealType> __bl,
5866 _Func __fw)
5867 : _M_param(__bl, __fw)
5868 { }
5869
5870 template<typename _Func>
5871 piecewise_linear_distribution(size_t __nw,
5872 _RealType __xmin, _RealType __xmax,
5873 _Func __fw)
5874 : _M_param(__nw, __xmin, __xmax, __fw)
5875 { }
5876
5877 explicit
5878 piecewise_linear_distribution(const param_type& __p)
5879 : _M_param(__p)
5880 { }
5881
5882 /**
5883 * Resets the distribution state.
5884 */
5885 void
5886 reset()
5887 { }
5888
5889 /**
5890 * @brief Return the intervals of the distribution.
5891 */
5892 std::vector<_RealType>
5893 intervals() const
5894 {
5895 if (_M_param._M_int.empty())
5896 {
5897 std::vector<_RealType> __tmp(2);
5898 __tmp[1] = _RealType(1);
5899 return __tmp;
5900 }
5901 else
5902 return _M_param._M_int;
5903 }
5904
5905 /**
5906 * @brief Return a vector of the probability densities of the
5907 * distribution.
5908 */
5909 std::vector<double>
5910 densities() const
5911 {
5912 return _M_param._M_den.empty()
5913 ? std::vector<double>(2, 1.0) : _M_param._M_den;
5914 }
5915
5916 /**
5917 * @brief Returns the parameter set of the distribution.
5918 */
5919 param_type
5920 param() const
5921 { return _M_param; }
5922
5923 /**
5924 * @brief Sets the parameter set of the distribution.
5925 * @param __param The new parameter set of the distribution.
5926 */
5927 void
5928 param(const param_type& __param)
5929 { _M_param = __param; }
5930
5931 /**
5932 * @brief Returns the greatest lower bound value of the distribution.
5933 */
5934 result_type
5935 min() const
5936 {
5937 return _M_param._M_int.empty()
5938 ? result_type(0) : _M_param._M_int.front();
5939 }
5940
5941 /**
5942 * @brief Returns the least upper bound value of the distribution.
5943 */
5944 result_type
5945 max() const
5946 {
5947 return _M_param._M_int.empty()
5948 ? result_type(1) : _M_param._M_int.back();
5949 }
5950
5951 /**
5952 * @brief Generating functions.
5953 */
5954 template<typename _UniformRandomNumberGenerator>
5955 result_type
5956 operator()(_UniformRandomNumberGenerator& __urng)
5957 { return this->operator()(__urng, _M_param); }
5958
5959 template<typename _UniformRandomNumberGenerator>
5960 result_type
5961 operator()(_UniformRandomNumberGenerator& __urng,
5962 const param_type& __p);
5963
5964 template<typename _ForwardIterator,
5965 typename _UniformRandomNumberGenerator>
5966 void
5967 __generate(_ForwardIterator __f, _ForwardIterator __t,
5968 _UniformRandomNumberGenerator& __urng)
5969 { this->__generate(__f, __t, __urng, _M_param); }
5970
5971 template<typename _ForwardIterator,
5972 typename _UniformRandomNumberGenerator>
5973 void
5974 __generate(_ForwardIterator __f, _ForwardIterator __t,
5975 _UniformRandomNumberGenerator& __urng,
5976 const param_type& __p)
5977 { this->__generate_impl(__f, __t, __urng, __p); }
5978
5979 template<typename _UniformRandomNumberGenerator>
5980 void
5981 __generate(result_type* __f, result_type* __t,
5982 _UniformRandomNumberGenerator& __urng,
5983 const param_type& __p)
5984 { this->__generate_impl(__f, __t, __urng, __p); }
5985
5986 /**
5987 * @brief Return true if two piecewise linear distributions have the
5988 * same parameters.
5989 */
5990 friend bool
5991 operator==(const piecewise_linear_distribution& __d1,
5992 const piecewise_linear_distribution& __d2)
5993 { return __d1._M_param == __d2._M_param; }
5994
5995 /**
5996 * @brief Inserts a %piecewise_linear_distribution random number
5997 * distribution @p __x into the output stream @p __os.
5998 *
5999 * @param __os An output stream.
6000 * @param __x A %piecewise_linear_distribution random number
6001 * distribution.
6002 *
6003 * @returns The output stream with the state of @p __x inserted or in
6004 * an error state.
6005 */
6006 template<typename _RealType1, typename _CharT, typename _Traits>
6007 friend std::basic_ostream<_CharT, _Traits>&
6008 operator<<(std::basic_ostream<_CharT, _Traits>& __os,
6009 const std::piecewise_linear_distribution<_RealType1>& __x);
6010
6011 /**
6012 * @brief Extracts a %piecewise_linear_distribution random number
6013 * distribution @p __x from the input stream @p __is.
6014 *
6015 * @param __is An input stream.
6016 * @param __x A %piecewise_linear_distribution random number
6017 * generator engine.
6018 *
6019 * @returns The input stream with @p __x extracted or in an error
6020 * state.
6021 */
6022 template<typename _RealType1, typename _CharT, typename _Traits>
6023 friend std::basic_istream<_CharT, _Traits>&
6024 operator>>(std::basic_istream<_CharT, _Traits>& __is,
6025 std::piecewise_linear_distribution<_RealType1>& __x);
6026
6027 private:
6028 template<typename _ForwardIterator,
6029 typename _UniformRandomNumberGenerator>
6030 void
6031 __generate_impl(_ForwardIterator __f, _ForwardIterator __t,
6032 _UniformRandomNumberGenerator& __urng,
6033 const param_type& __p);
6034
6035 param_type _M_param;
6036 };
6037
6038 /**
6039 * @brief Return true if two piecewise linear distributions have
6040 * different parameters.
6041 */
6042 template<typename _RealType>
6043 inline bool
6044 operator!=(const std::piecewise_linear_distribution<_RealType>& __d1,
6045 const std::piecewise_linear_distribution<_RealType>& __d2)
6046 { return !(__d1 == __d2); }
6047
6048
6049 /* @} */ // group random_distributions_poisson
6050
6051 /* @} */ // group random_distributions
6052
6053 /**
6054 * @addtogroup random_utilities Random Number Utilities
6055 * @ingroup random
6056 * @{
6057 */
6058
6059 /**
6060 * @brief The seed_seq class generates sequences of seeds for random
6061 * number generators.
6062 */
6063 class seed_seq
6064 {
6065 public:
6066 /** The type of the seed vales. */
6067 typedef uint_least32_t result_type;
6068
6069 /** Default constructor. */
6070 seed_seq() noexcept
6071 : _M_v()
6072 { }
6073
6074 template<typename _IntType>
6075 seed_seq(std::initializer_list<_IntType> __il);
6076
6077 template<typename _InputIterator>
6078 seed_seq(_InputIterator __begin, _InputIterator __end);
6079
6080 // generating functions
6081 template<typename _RandomAccessIterator>
6082 void
6083 generate(_RandomAccessIterator __begin, _RandomAccessIterator __end);
6084
6085 // property functions
6086 size_t size() const noexcept
6087 { return _M_v.size(); }
6088
6089 template<typename _OutputIterator>
6090 void
6091 param(_OutputIterator __dest) const
6092 { std::copy(_M_v.begin(), _M_v.end(), __dest); }
6093
6094 // no copy functions
6095 seed_seq(const seed_seq&) = delete;
6096 seed_seq& operator=(const seed_seq&) = delete;
6097
6098 private:
6099 std::vector<result_type> _M_v;
6100 };
6101
6102 /* @} */ // group random_utilities
6103
6104 /* @} */ // group random
6105
6106 _GLIBCXX_END_NAMESPACE_VERSION
6107 } // namespace std
6108
6109 #endif
6110