re PR libstdc++/33815 (tr1::uniform_int isn't uniform)
authorPaolo Carlini <pcarlini@suse.de>
Fri, 19 Oct 2007 17:36:03 +0000 (17:36 +0000)
committerPaolo Carlini <paolo@gcc.gnu.org>
Fri, 19 Oct 2007 17:36:03 +0000 (17:36 +0000)
2007-10-19  Paolo Carlini  <pcarlini@suse.de>

PR libstdc++/33815
* include/tr1_impl/random
(uniform_int<>::_M_call(_UniformRandomNumberGenerator&, result_type,
result_type, true_type)): Avoid the modulo (which uses the low-order
bits).

From-SVN: r129493

libstdc++-v3/ChangeLog
libstdc++-v3/include/tr1_impl/random

index b12b8b383066d03e4096e6a36c72b3a9b955447d..b4f58acbc0991d081976c6386ee7cabcc9c8d9f0 100644 (file)
@@ -1,3 +1,11 @@
+2007-10-19  Paolo Carlini  <pcarlini@suse.de>
+
+       PR libstdc++/33815
+       * include/tr1_impl/random
+       (uniform_int<>::_M_call(_UniformRandomNumberGenerator&, result_type,
+       result_type, true_type)): Avoid the modulo (which uses the low-order
+       bits).
+
 2007-10-19  Paolo Carlini  <pcarlini@suse.de>
 
        * include/bits/stl_algobase.h (struct __cm_assign,
index e855307dace7b180905bcd785bd079fdf5591396..f44b17f97924d9c4cda59b895287e61c44ac02db 100644 (file)
@@ -1605,9 +1605,13 @@ _GLIBCXX_BEGIN_NAMESPACE_TR1
         _M_call(_UniformRandomNumberGenerator& __urng,
                result_type __min, result_type __max, true_type)
         {
+         // XXX Must be fixed to also work when __urng.max() - __urng.min()
+         // is smaller than __max - __min.
          typedef typename __gnu_cxx::__add_unsigned<typename
            _UniformRandomNumberGenerator::result_type>::__type __utype;
-         return result_type(__utype(__urng()) % (__max - __min + 1)) + __min; 
+         return result_type((__max - __min + 1.0L) * __utype(__urng())
+                            / (__utype(__urng.max())
+                               - __utype(__urng.min()) + 1.0L)) + __min;
        }
 
       template<typename _UniformRandomNumberGenerator>