aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPaolo Carlini <pcarlini@suse.de>2006-08-29 11:46:54 +0000
committerPaolo Carlini <paolo@gcc.gnu.org>2006-08-29 11:46:54 +0000
commita3b6119721e9344233ac684940ea4cc0ee79e9c5 (patch)
tree0b05bba61c2ae51b0060ee8beaae22c3e242dbe1
parentd99cc025420e145199dee250bb957835631f04ab (diff)
downloadgcc-a3b6119721e9344233ac684940ea4cc0ee79e9c5.zip
gcc-a3b6119721e9344233ac684940ea4cc0ee79e9c5.tar.gz
gcc-a3b6119721e9344233ac684940ea4cc0ee79e9c5.tar.bz2
random (subtract_with_carry_01<>::_M_initialize_npows): New.
2006-08-29 Paolo Carlini <pcarlini@suse.de> * include/tr1/random (subtract_with_carry_01<>::_M_initialize_npows): New. (subtract_with_carry_01<>::subtract_with_carry_01(), subtract_with_carry_01<>::subtract_with_carry_01(unsigned long), subtract_with_carry_01<>::subtract_with_carry_01(_Gen&)): Use it. * include/tr1/random.tcc: Define. * include/tr1/random (xor_combine<>::_M_initialize_max()): New. (xor_combine<>::xor_combine(), xor_combine<>::xor_combine(const base1_type&, const base2_type&), xor_combine<>::xor_combine(unsigned long), xor_combine<>::xor_combine(_Gen&)): Use it. (xor_combine<>::min, xor_combine<>::max): Adjust. * include/tr1/random.tcc: Define. From-SVN: r116559
-rw-r--r--libstdc++-v3/ChangeLog16
-rw-r--r--libstdc++-v3/include/tr1/random46
-rw-r--r--libstdc++-v3/include/tr1/random.tcc54
3 files changed, 95 insertions, 21 deletions
diff --git a/libstdc++-v3/ChangeLog b/libstdc++-v3/ChangeLog
index a7bc852..cf8546c 100644
--- a/libstdc++-v3/ChangeLog
+++ b/libstdc++-v3/ChangeLog
@@ -1,3 +1,19 @@
+2006-08-29 Paolo Carlini <pcarlini@suse.de>
+
+ * include/tr1/random (subtract_with_carry_01<>::_M_initialize_npows):
+ New.
+ (subtract_with_carry_01<>::subtract_with_carry_01(),
+ subtract_with_carry_01<>::subtract_with_carry_01(unsigned long),
+ subtract_with_carry_01<>::subtract_with_carry_01(_Gen&)): Use it.
+ * include/tr1/random.tcc: Define.
+
+ * include/tr1/random (xor_combine<>::_M_initialize_max()): New.
+ (xor_combine<>::xor_combine(), xor_combine<>::xor_combine(const
+ base1_type&, const base2_type&), xor_combine<>::xor_combine(unsigned
+ long), xor_combine<>::xor_combine(_Gen&)): Use it.
+ (xor_combine<>::min, xor_combine<>::max): Adjust.
+ * include/tr1/random.tcc: Define.
+
2006-08-29 Benjamin Kosnik <bkoz@redhat.com>
* acinclude.m4(glibcxx_PCHFLAGS): Set to stdtr1c++.h.
diff --git a/libstdc++-v3/include/tr1/random b/libstdc++-v3/include/tr1/random
index b90d323..8ffdf16 100644
--- a/libstdc++-v3/include/tr1/random
+++ b/libstdc++-v3/include/tr1/random
@@ -944,7 +944,10 @@ _GLIBCXX_BEGIN_NAMESPACE(tr1)
* number generator.
*/
subtract_with_carry_01()
- { this->seed(); }
+ {
+ this->seed();
+ _M_initialize_npows();
+ }
/**
* Constructs an explicitly seeded % subtract_with_carry_01 random number
@@ -952,7 +955,10 @@ _GLIBCXX_BEGIN_NAMESPACE(tr1)
*/
explicit
subtract_with_carry_01(unsigned long __value)
- { this->seed(__value); }
+ {
+ this->seed(__value);
+ _M_initialize_npows();
+ }
/**
* Constructs a % subtract_with_carry_01 random number generator engine
@@ -962,7 +968,10 @@ _GLIBCXX_BEGIN_NAMESPACE(tr1)
*/
template<class _Gen>
subtract_with_carry_01(_Gen& __g)
- { this->seed(__g); }
+ {
+ this->seed(__g);
+ _M_initialize_npows();
+ }
/**
* Seeds the initial state @f$ x_0 @f$ of the random number generator.
@@ -1081,6 +1090,9 @@ _GLIBCXX_BEGIN_NAMESPACE(tr1)
seed(_Gen& __g, false_type);
private:
+ void
+ _M_initialize_npows();
+
static const int __n = (__w + 31) / 32;
_UInt32Type _M_x[long_lag][__n];
@@ -1372,17 +1384,22 @@ _GLIBCXX_BEGIN_NAMESPACE(tr1)
static const int shift2 = __s2;
// constructors and member function
- xor_combine() { }
+ xor_combine()
+ : _M_b1(), _M_b2()
+ { _M_initialize_max(); }
xor_combine(const base1_type& __rng1, const base2_type& __rng2)
- : _M_b1(__rng1), _M_b2(__rng2) { }
+ : _M_b1(__rng1), _M_b2(__rng2)
+ { _M_initialize_max(); }
xor_combine(unsigned long __s)
- : _M_b1(__s), _M_b2(__s + 1) { }
+ : _M_b1(__s), _M_b2(__s + 1)
+ { _M_initialize_max(); }
template<class _Gen>
xor_combine(_Gen& __g)
- : _M_b1(__g), _M_b2(__g) { }
+ : _M_b1(__g), _M_b2(__g)
+ { _M_initialize_max(); }
void
seed()
@@ -1407,15 +1424,14 @@ _GLIBCXX_BEGIN_NAMESPACE(tr1)
base2() const
{ return _M_b2; }
- // FIXME: Cannot be always correct. FWIW, the solution in N2032
- // in practice isn't much better..
+ // XXX Per N2032, but aren't always right...
result_type
min() const
- { return _M_b1.min() ^ _M_b2.min(); }
+ { return 0; }
result_type
max() const
- { return _M_b1.max() | _M_b2.max(); }
+ { return _M_max; }
/**
* Gets the next random number in the sequence.
@@ -1492,8 +1508,12 @@ _GLIBCXX_BEGIN_NAMESPACE(tr1)
_UniformRandomNumberGenerator21, __s21>& __x);
private:
- base1_type _M_b1;
- base2_type _M_b2;
+ void
+ _M_initialize_max();
+
+ base1_type _M_b1;
+ base2_type _M_b2;
+ result_type _M_max;
};
diff --git a/libstdc++-v3/include/tr1/random.tcc b/libstdc++-v3/include/tr1/random.tcc
index b95a5f8..e6d4d94 100644
--- a/libstdc++-v3/include/tr1/random.tcc
+++ b/libstdc++-v3/include/tr1/random.tcc
@@ -448,6 +448,19 @@ _GLIBCXX_BEGIN_NAMESPACE(tr1)
template<typename _RealType, int __w, int __s, int __r>
void
subtract_with_carry_01<_RealType, __w, __s, __r>::
+ _M_initialize_npows()
+ {
+ for (int __j = 0; __j < __n; ++__j)
+#if _GLIBCXX_USE_C99_MATH_TR1
+ _M_npows[__j] = std::tr1::ldexp(_RealType(1), -__w + __j * 32);
+#else
+ _M_npows[__j] = std::pow(_RealType(2), -__w + __j * 32);
+#endif
+ }
+
+ template<typename _RealType, int __w, int __s, int __r>
+ void
+ subtract_with_carry_01<_RealType, __w, __s, __r>::
seed(unsigned long __value)
{
if (__value == 0)
@@ -484,14 +497,6 @@ _GLIBCXX_BEGIN_NAMESPACE(tr1)
}
_M_p = 0;
-
- // Initialize the array holding the negative powers of 2.
- for (int __j = 0; __j < __n; ++__j)
-#if _GLIBCXX_USE_C99_MATH_TR1
- _M_npows[__j] = std::tr1::ldexp(_RealType(1), -__w + __j * 32);
-#else
- _M_npows[__j] = std::pow(_RealType(2), -__w + __j * 32);
-#endif
}
template<typename _RealType, int __w, int __s, int __r>
@@ -638,6 +643,39 @@ _GLIBCXX_BEGIN_NAMESPACE(tr1)
template<class _UniformRandomNumberGenerator1, int __s1,
+ class _UniformRandomNumberGenerator2, int __s2>
+ void
+ xor_combine<_UniformRandomNumberGenerator1, __s1,
+ _UniformRandomNumberGenerator2, __s2>::
+ _M_initialize_max()
+ {
+ const int __lshift = std::abs(__s1 - __s2);
+
+ result_type __m1 = _M_b1.max() - _M_b1.min();
+ result_type __m2 = _M_b2.max() - _M_b2.min();
+
+ // NB: in TR1 s1 is not required to be >= s2.
+ if (__s1 >= __s2)
+ __m1 <<= __lshift;
+ else
+ __m2 <<= __lshift;
+
+ result_type __a = __m1 & __m2;
+ const result_type __b = __m1 | __m2;
+
+ result_type __c = 0;
+ if (__a)
+ {
+ result_type __k;
+ for (__k = 0; __a != 1; __a >>= 1)
+ ++__k;
+ __c = (result_type(1) << __k) - 1;
+ }
+
+ _M_max = (__c | __b) << __lshift;
+ }
+
+ template<class _UniformRandomNumberGenerator1, int __s1,
class _UniformRandomNumberGenerator2, int __s2,
typename _CharT, typename _Traits>
std::basic_ostream<_CharT, _Traits>&