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