55 #define RANDOMLIB_RANDOM_CPP 1
60 #define RANDOMLIB_BUILDING_LIBRARY 1
64 #if defined(_MSC_VER) || defined(__MINGW32__)
65 #define RANDOMLIB_WINDOWS 1
67 #define RANDOMLIB_WINDOWS 0
74 #if !RANDOMLIB_WINDOWS
81 #define getpid _getpid
82 #define gmtime_r(t,g) gmtime_s(g,t)
85 #if RANDOMLIB_WINDOWS || defined(__CYGWIN__)
86 #define strtoull strtoul
91 # pragma warning (disable: 4127)
102 unsigned char buf[4];
104 buf[3] = (
unsigned char)(x);
105 buf[2] = (
unsigned char)(x >>= 8);
106 buf[1] = (
unsigned char)(x >>= 8);
107 buf[0] = (
unsigned char)(x >>= 8);
108 os.write(reinterpret_cast<const char *>(buf), 4);
110 const int longsperline = 72/9;
113 std::ostringstream str;
117 str << (cnt % longsperline ?
' ' :
'\n');
118 str << std::hex << x;
127 unsigned char buf[4];
128 is.read(reinterpret_cast<char *>(buf), 4);
137 std::istringstream str(s);
138 str >> std::hex >> x;
165 !std::numeric_limits<seed_type>::is_signed &&
166 std::numeric_limits<seed_type>::digits >= 32,
167 "seed_type is a bad type");
172 std::ifstream f(
"/dev/urandom", std::ios::binary | std::ios::in);
175 f.read(reinterpret_cast<char *>(&t),
sizeof(t));
179 for (
size_t i = v.size(); i--;)
185 std::vector<seed_type> v;
188 #if !RANDOMLIB_WINDOWS
190 if (gettimeofday(&tv, 0) == 0)
194 if (QueryPerformanceCounter((LARGE_INTEGER *)&taux)) {
201 const time_t tim = std::time(0);
205 #if !RANDOMLIB_WINDOWS
211 #if !defined(__MINGW32__)
216 tm* gt = gmtime(&tim);
222 std::transform(v.begin(), v.end(), v.begin(), seed_t::cast<seed_type>);
226 std::vector<RandomSeed::seed_type>
228 std::vector<seed_type> v(0);
229 const char* c = s.c_str();
231 std::string::size_type p = 0;
233 p = s.find_first_of(
"0123456789", p);
234 if (p == std::string::npos)
244 template<
class Algorithm,
class Mixer>
248 STATIC_ASSERT(std::numeric_limits<typename mixer_t::type>::radix == 2 &&
249 !std::numeric_limits<typename mixer_t::type>::is_signed &&
250 std::numeric_limits<typename mixer_t::type>::digits >=
252 "mixer_type is a bad type");
254 STATIC_ASSERT(std::numeric_limits<result_type>::radix == 2 &&
255 !std::numeric_limits<result_type>::is_signed &&
256 std::numeric_limits<result_type>::digits >= width,
257 "engine_type is a bad type");
260 "Mixer width must be 32 or 64");
263 "Algorithm width must be 32 or 64");
267 sizeof(_stateu) ==
sizeof(_state),
268 "Same bit-widths but different storage");
273 sizeof(_stateu) >=
sizeof(_state),
274 "Narrow data type uses less storage");
277 sizeof(_stateu) <=
sizeof(_state),
278 "Narrow data type uses less storage");
283 "Storage mismatch with internal engine data type");
286 Mixer::SeedToState(_seed, _stateu, NU);
289 if (mixer_t::width < width) {
290 for (
size_t i = 0; i < N; ++i)
292 _state[i] = result_type(_stateu[2*i]) |
293 result_type(_stateu[2*i + 1]) <<
294 (mixer_t::width < width ? mixer_t::width : 0);
295 }
else if (mixer_t::width > width) {
296 for (
size_t i = N; i--;)
298 _state[i] = result_t::cast(_stateu[i>>1] >> width * (i&1u));
301 Algorithm::NormalizeState(_state);
308 RandomEngine<Algorithm, Mixer>::Check(u64::type v, u32::type e,
311 throw RandomErr(Name() +
": Unknown version");
312 if (e != Algorithm::version)
313 throw RandomErr(Name() +
": Algorithm mismatch");
314 if (m != Mixer::version)
315 throw RandomErr(Name() +
": Mixer mismatch");
317 u64::CheckSum(v, check);
318 u32::CheckSum(e, check);
319 u32::CheckSum(m, check);
320 u32::CheckSum(u32::type(_seed.size()), check);
321 for (std::vector<seed_type>::const_iterator n = _seed.begin();
322 n != _seed.end(); ++n) {
323 if (*n != seed_t::cast(*n))
324 throw RandomErr(Name() +
": Illegal seed value");
325 u32::CheckSum(u32::type(*n), check);
327 u32::CheckSum(_ptr, check);
328 if (_stride == 0 || _stride > UNINIT/2)
329 throw RandomErr(Name() +
": Invalid stride");
330 u32::CheckSum(_stride, check);
331 if (_ptr != UNINIT) {
332 if (_ptr >= N + _stride)
333 throw RandomErr(Name() +
": Invalid pointer");
334 u64::CheckSum(_rounds, check);
335 Algorithm::CheckState(_state, check);
340 template<
typename Algorithm,
typename Mixer>
343 u32::type versione, versionm, t;
344 u64::Read32(is, bin, versionr);
345 u32::Read32(is, bin, versione);
346 u32::Read32(is, bin, versionm);
347 u32::Read32(is, bin, t);
348 _seed.resize(
size_t(t));
349 for (std::vector<seed_type>::iterator n = _seed.begin();
350 n != _seed.end(); ++n) {
351 u32::Read32(is, bin, t);
354 u32::Read32(is, bin, t);
357 u32::Read32(is, bin, t);
358 _stride = unsigned(t);
359 if (_ptr != UNINIT) {
361 u64::Read32(is, bin, p);
362 _rounds = (
long long)(p);
364 _rounds <<= 63 - std::numeric_limits<long long>::digits;
365 _rounds >>= 63 - std::numeric_limits<long long>::digits;
366 for (
unsigned i = 0; i < N; ++i)
367 result_t::Read32(is, bin, _state[i]);
369 u32::Read32(is, bin, t);
370 if (t != Check(versionr, versione, versionm))
371 throw RandomErr(Name() +
": Checksum failure");
374 template<
typename Algorithm,
typename Mixer>
377 u32::type check = Check(version, Algorithm::version, Mixer::version);
379 u64::Write32(os, bin, c, version);
380 u32::Write32(os, bin, c, Algorithm::version);
381 u32::Write32(os, bin, c, Mixer::version);
382 u32::Write32(os, bin, c,
u32::type(_seed.size()));
383 for (std::vector<seed_type>::const_iterator n = _seed.begin();
384 n != _seed.end(); ++n)
386 u32::Write32(os, bin, c, _ptr);
387 u32::Write32(os, bin, c, _stride);
388 if (_ptr != UNINIT) {
389 u64::Write32(os, bin, c, u64::type(_rounds));
390 for (
unsigned i = 0; i < N; ++i)
391 result_t::Write32(os, bin, c, _state[i]);
393 u32::Write32(os, bin, c, check);
396 template<
typename Algorithm,
typename Mixer>
401 const long long ncount = n + Count();
402 long long nrounds = ncount / N;
403 int nptr = int(ncount - nrounds * N);
410 }
else if (nptr == 0 && nrounds > _rounds) {
414 if (nrounds != _rounds)
415 Algorithm::Transition(nrounds - _rounds, _statev);
420 template<
typename Algorithm,
typename Mixer>
425 if (SelfTestResult(0) && x != SelfTestResult(1))
426 throw RandomErr(Name() +
": Incorrect result with seed " +
428 seed_type s[] = {0x1234U, 0x5678U, 0x9abcU, 0xdef0U};
434 std::ostringstream stream;
440 std::istringstream stream(save);
445 std::ostringstream stream;
446 g.
Save(stream,
true);
450 std::istringstream stream(save);
452 h.
Load(stream,
true);
455 if (SelfTestResult(0) && x != SelfTestResult(2))
456 throw RandomErr(Name() +
": Incorrect result with seed " +
460 throw RandomErr(Name() +
": Comparison failure");
466 SelfTestResult(
unsigned i)
throw() {
468 i == 1 ? 4123659995UL : 3016432305UL;
472 RandomEngine<MT19937<Random_u64>, MixerMT0<Random_u64> >::
473 SelfTestResult(
unsigned i)
throw() {
475 i == 1 ? 9981545732273789042ULL : 1384037754719008581ULL;
479 RandomEngine<MT19937<Random_u32>, MixerMT1<Random_u32> >::
480 SelfTestResult(
unsigned i)
throw() {
482 i == 1 ? 4123659995UL : 2924523180UL;
486 RandomEngine<MT19937<Random_u64>, MixerMT1<Random_u64> >::
487 SelfTestResult(
unsigned i)
throw() {
489 i == 1 ? 9981545732273789042ULL : 5481486777409645478ULL;
493 RandomEngine<MT19937<Random_u32>, MixerSFMT>::
494 SelfTestResult(
unsigned i)
throw() {
496 i == 1 ? 666528879UL : 2183745132UL;
500 RandomEngine<MT19937<Random_u64>, MixerSFMT>::
501 SelfTestResult(
unsigned i)
throw() {
503 i == 1 ? 12176471137395770412ULL : 66914054428611861ULL;
507 RandomEngine<SFMT19937<Random_u32>, MixerSFMT>::
508 SelfTestResult(
unsigned i)
throw() {
510 i == 1 ? 2695024307UL : 782200760UL;
514 RandomEngine<SFMT19937<Random_u64>, MixerSFMT>::
515 SelfTestResult(
unsigned i)
throw() {
517 i == 1 ? 1464461649847485149ULL : 5050640804923595109ULL;
524 mixer_type state[],
unsigned n)
throw() {
528 const unsigned s = unsigned(seed.size());
529 const unsigned w = mixer_t::width;
531 mixer_type r = s ? a1 + mixer_type(0) : a0 + mixer_type(0);
533 for (
unsigned k = 1; k < n; ++k) {
534 r = b * (r ^ r >> (w - 2)) + k;
539 const unsigned m = mixer_t::width / 32,
543 for (
unsigned k = (n > s2 ? n : s2), j = 0;
544 k; --k, i1 = i1 == n - 1 ? 1 : i1 + 1,
545 j = j == s2 - 1 ? 0 : j + 1 ) {
546 r = state[i1] ^ c * (r ^ r >> (w - 2));
547 r += j + mixer_type(seed[m * j]) +
548 (m == 1 || 2 * j + 1 == s ? mixer_type(0) :
549 mixer_type(seed[m * j + 1]) << (w - 32));
553 for (
unsigned k = n - 1; k; --k,
554 i1 = i1 == n - 1 ? 1 : i1 + 1) {
555 r = state[i1] ^ d * (r ^ r >> (w - 2));
566 mixer_type state[],
unsigned n)
throw() {
572 const unsigned s = unsigned(seed.size());
573 const unsigned w = mixer_t::width;
575 mixer_type r = (a + s) & mask;
577 for (
unsigned k = 1; k < n; ++k) {
578 r = b * (r ^ r >> (w - 2)) + k;
583 const unsigned m = mixer_t::width / 32,
586 for (
unsigned k = (n > s2 ? n : s2), j = 0;
587 k; --k, i1 = i1 == n - 1 ? 0 : i1 + 1,
588 j = j == s2 - 1 ? 0 : j + 1 ) {
589 r = state[i1] ^ c * (r ^ r >> (w - 2));
590 r += j + mixer_type(seed[m * j]) +
591 (m == 1 || 2 * j + 1 == s ? mixer_type(0) :
592 mixer_type(seed[m * j + 1]) << (w - 32));
596 for (
unsigned k = n; k; --k,
597 i1 = i1 == n - 1 ? 0 : i1 + 1) {
598 r = state[i1] ^ d * (r ^ r >> (w - 2));
607 mixer_type state[],
unsigned n)
throw() {
614 const unsigned s = unsigned(seed.size()),
618 lag = n >= 623 ? 11 : (n >= 68 ? 7 : (n >= 39 ? 5 :
619 (n >= 7 ? 3 : (n - 1)/2))),
621 count = s + 1 > n ? s + 1 : n;
623 std::fill(state, state + n, mixer_type(a));
624 const unsigned w = mixer_t::width;
626 unsigned i = 0, k = (n - lag) / 2, l = k + lag;
627 mixer_type r = state[n - 1];
628 for (
unsigned j = 0; j < count; ++j,
629 i = i == n - 1 ? 0 : i + 1,
630 k = k == n - 1 ? 0 : k + 1,
631 l = l == n - 1 ? 0 : l + 1) {
636 r ^= state[i] ^ state[k];
638 r = b * (r ^ r >> (w - 5));
640 r += i + (j > s ? 0 : (j ? mixer_type(seed[j - 1]) : s));
645 for (
unsigned j = n; j; --j,
646 i = i == n - 1 ? 0 : i + 1,
647 k = k == n - 1 ? 0 : k + 1,
648 l = l == n - 1 ? 0 : l + 1) {
652 r += state[i] + state[k];
654 r = c * (r ^ r >> (w - 5));
668 #define MT19937_STEP(I, J, K) statev[I] = statev[K] ^ \
669 (statev[J] & engine_type(1) ? magic : engine_type(0)) ^ \
670 ((statev[I] & upper) | (statev[J] & lower)) >> 1
679 #define MT19937_REVSTEP(I, J, K) { \
680 engine_type q = statev[J] ^ statev[K], s = q >> (width - 1); \
681 q = (q ^ (s ? magic : engine_type(0))) << 1 | s; \
682 statev[I] = (p & upper) | (q & lower); \
686 template<
class RandomType>
690 for (; count; --count) {
694 for (; i < N - 1; ++i)
MT19937_STEP(i, i + 1, i + M - N);
698 for (; count; ++count) {
700 engine_type p = statev[0];
711 #undef MT19937_REVSTEP
713 template<
class RandomType>
720 while (i < N && state[i] == 0)
723 state[0] = engine_type(1) << (width - 1);
729 engine_type q = state[N - 1] ^ state[M - 1], s = q >> (width - 1);
730 q = (q ^ (s ? magic : engine_type(0))) << 1 | s;
731 state[0] = (state[0] & upper) | (q & lower);
734 template<
class RandomType>
739 for (
unsigned i = 0; i < N; ++i) {
740 engine_t::CheckSum(state[i], c);
744 throw RandomErr(
"MT19937: All-zero state");
749 engine_type q = state[N - 1] ^ state[M - 1], s = q >> (width - 1);
750 q = (q ^ (s ? magic : engine_type(0))) << 1 | s;
751 if ((q ^ state[0]) & lower)
752 throw RandomErr(
"MT19937: Invalid state");
757 #if defined(HAVE_SSE2) && HAVE_SSE2
790 #define SFMT19937_STEP128(I, J) { \
791 internal_type x = _mm_load_si128(statev + I), \
792 y = _mm_srli_epi32(statev[J], 11), \
793 z = _mm_srli_si128(s, 1); \
794 s = _mm_slli_epi32(r, 18); \
795 z = _mm_xor_si128(z, x); \
796 x = _mm_slli_si128(x, 1); \
797 z = _mm_xor_si128(z, s); \
798 y = _mm_and_si128(y, m); \
799 z = _mm_xor_si128(z, x); \
801 r = _mm_xor_si128(z, y); \
802 _mm_store_si128(statev + I, r); \
830 #define SFMT19937_REVSTEP128(I, J, K, L) { \
831 internal_type x = _mm_load_si128(statev + I), \
832 y = _mm_srli_epi32(statev[J], 11), \
833 z = _mm_slli_epi32(statev[L], 18); \
834 y = _mm_and_si128(y, m); \
835 x = _mm_xor_si128(x, _mm_srli_si128(statev[K], 1)); \
836 x = _mm_xor_si128(x, z); \
837 x = _mm_xor_si128(x, y); \
838 x = _mm_xor_si128(_mm_slli_si128(x, 8), x); \
839 x = _mm_xor_si128(_mm_slli_si128(x, 4), x); \
840 x = _mm_xor_si128(_mm_slli_si128(x, 2), x); \
841 x = _mm_xor_si128(_mm_slli_si128(x, 1), x); \
842 _mm_store_si128(statev + I, x); \
845 template<
class RandomType>
847 internal_type statev[])
849 const internal_type m = _mm_set_epi32(magic3, magic2, magic1, magic0);
851 internal_type s = _mm_load_si128(statev + N128 - 2),
852 r = _mm_load_si128(statev + N128 - 1);
853 for (; count; --count) {
855 for (; i + M128 < N128; ++i) SFMT19937_STEP128(i, i + M128 );
856 for (; i < N128 ; ++i) SFMT19937_STEP128(i, i + M128 - N128);
858 }
else if (count < 0)
859 for (; count; ++count) {
861 for (; i + M128 > N128;) {
862 --i; SFMT19937_REVSTEP128(i, i + M128 - N128, i - 2, i - 1);
865 --i; SFMT19937_REVSTEP128(i, i + M128, i - 2, i - 1);
867 SFMT19937_REVSTEP128(1, M128 + 1, N128 - 1, 0 );
868 SFMT19937_REVSTEP128(0, M128 , N128 - 2, N128 - 1);
872 #undef SFMT19937_STEP128
873 #undef SFMT19937_REVSTEP128
875 #elif defined(HAVE_ALTIVEC) && HAVE_ALTIVEC
885 #define ALTIVEC_PERM(X, P) vec_perm(X, P, P)
887 #define SFMT19937_STEP128(I, J) { \
888 internal_type x = statev[I], \
889 z = vec_xor(vec_xor(ALTIVEC_PERM(s, right1), x), \
890 vec_sl(r, bitleft)); \
893 vec_xor(ALTIVEC_PERM(x, left1), \
894 vec_and(vec_sr(statev[J], bitright), \
899 #define SFMT19937_REVSTEP128(I, J, K, L) { \
900 internal_type x = statev[I], \
901 y = vec_sr(statev[J], bitright), \
902 z = vec_sl(statev[L], bitleft); \
903 y = vec_and(y, magic); \
904 x = vec_xor(x, ALTIVEC_PERM(statev[K], right1)); \
907 x = vec_xor(ALTIVEC_PERM(x, left8), x); \
908 x = vec_xor(ALTIVEC_PERM(x, left4), x); \
909 x = vec_xor(ALTIVEC_PERM(x, left2), x); \
910 statev[I] = vec_xor(ALTIVEC_PERM(x, left1), x); \
913 template<
class RandomType>
915 internal_type statev[])
917 const internal_type magic = width == 32 ?
918 (vector unsigned)(magic0, magic1, magic2, magic3) :
919 (vector unsigned)(magic1, magic0, magic3, magic2),
920 bitleft = (vector unsigned)(18, 18, 18, 18),
921 bitright = (vector unsigned)(11, 11, 11, 11);
946 const vector
unsigned char left1 = width == 32 ?
947 (vector
unsigned char)(1,2,3,23, 5,6,7,0, 9,10,11,4, 13,14,15,8) :
948 (vector
unsigned char)(1,2,3,4,5,6,7,31, 9,10,11,12,13,14,15,0),
949 right1 = width == 32 ?
950 (vector
unsigned char)(7,0,1,2, 11,4,5,6, 15,8,9,10, 17,12,13,14) :
951 (vector
unsigned char)(15,0,1,2,3,4,5,6, 17,8,9,10,11,12,13,14);
953 internal_type s = statev[N128 - 2],
954 r = statev[N128 - 1];
955 for (; count; --count) {
957 for (; i + M128 < N128; ++i) SFMT19937_STEP128(i, i + M128 );
958 for (; i < N128 ; ++i) SFMT19937_STEP128(i, i + M128 - N128);
960 }
else if (count < 0) {
962 const vector
unsigned char left2 = width == 32 ?
963 (vector
unsigned char)(2,3,22,22, 6,7,0,1, 10,11,4,5, 14,15,8,9) :
964 (vector
unsigned char)(2,3,4,5,6,7,30,30, 10,11,12,13,14,15,0,1),
965 left4 = width == 32 ?
966 (vector
unsigned char)(20,20,20,20, 0,1,2,3, 4,5,6,7, 8,9,10,11) :
967 (vector
unsigned char)(4,5,6,7,28,28,28,28, 12,13,14,15,0,1,2,3),
968 left8 = (vector
unsigned char)(24,24,24,24,24,24,24,24,0,1,2,3,4,5,6,7);
969 for (; count; ++count) {
971 for (; i + M128 > N128;) {
972 --i; SFMT19937_REVSTEP128(i, i + M128 - N128, i - 2, i - 1);
975 --i; SFMT19937_REVSTEP128(i, i + M128, i - 2, i - 1);
977 SFMT19937_REVSTEP128(1, M128 + 1, N128 - 1, 0 );
978 SFMT19937_REVSTEP128(0, M128 , N128 - 2, N128 - 1);
983 #undef SFMT19937_STEP128
984 #undef SFMT19937_REVSTEP128
987 #else // neither HAVE_SSE2 or HAVE_ALTIVEC
989 #define SFMT19937_STEP32(I, J) { \
990 internal_type t = statev[I] ^ statev[I] << 8 ^ \
991 (statev[J] >> 11 & magic0) ^ \
992 (s0 >> 8 | s1 << 24) ^ r0 << 18; \
993 s0 = r0; r0 = t & mask; \
994 t = statev[I + 1] ^ \
995 (statev[I + 1] << 8 | statev[I] >> 24) ^ \
996 (statev[J + 1] >> 11 & magic1) ^ \
997 (s1 >> 8 | s2 << 24) ^ r1 << 18; \
998 s1 = r1; r1 = t & mask; \
999 t = statev[I + 2] ^ \
1000 (statev[I + 2] << 8 | statev[I + 1] >> 24) ^ \
1001 (statev[J + 2] >> 11 & magic2) ^ \
1002 (s2 >> 8 | s3 << 24) ^ r2 << 18; \
1003 s2 = r2; r2 = t & mask; \
1004 t = statev[I + 3] ^ \
1005 (statev[I + 3] << 8 | statev[I + 2] >> 24) ^ \
1006 (statev[J + 3] >> 11 & magic3) ^ s3 >> 8 ^ r3 << 18; \
1007 s3 = r3; r3 = t & mask; \
1008 statev[I ] = r0; statev[I + 1] = r1; \
1009 statev[I + 2] = r2; statev[I + 3] = r3; \
1012 #define SFMT19937_REVSTEP32(I, J, K, L) { \
1014 t0 = (statev[I] ^ (statev[J] >> 11 & magic0) ^ \
1015 (statev[K] >> 8 | statev[K + 1] << 24) ^ \
1016 statev[L] << 18) & mask, \
1017 t1 = (statev[I + 1] ^ \
1018 (statev[J + 1] >> 11 & magic1) ^ \
1019 (statev[K + 1] >> 8 | statev[K + 2] << 24) ^ \
1020 statev[L + 1] << 18) & mask, \
1021 t2 = (statev[I + 2] ^ \
1022 (statev[J + 2] >> 11 & magic2) ^ \
1023 (statev[K + 2] >> 8 | statev[K + 3] << 24) ^ \
1024 statev[L + 2] << 18) & mask, \
1025 t3 = (statev[I + 3] ^ \
1026 (statev[J + 3] >> 11 & magic3) ^ \
1027 statev[K + 3] >> 8 ^ \
1028 statev[L + 3] << 18) & mask; \
1029 t3 ^= t1; t2 ^= t0; t3 ^= t2; t2 ^= t1; t1 ^= t0; \
1030 t3 ^= t2 >> 16 | (t3 << 16 & mask); \
1031 t2 ^= t1 >> 16 | (t2 << 16 & mask); \
1032 t1 ^= t0 >> 16 | (t1 << 16 & mask); \
1033 t0 ^= t0 << 16 & mask; \
1034 statev[I ] = t0 ^ (t0 << 8 & mask); \
1035 statev[I + 1] = t1 ^ (t0 >> 24 | (t1 << 8 & mask)); \
1036 statev[I + 2] = t2 ^ (t1 >> 24 | (t2 << 8 & mask)); \
1037 statev[I + 3] = t3 ^ (t2 >> 24 | (t3 << 8 & mask)); \
1047 s0 = statev[N - 8], s1 = statev[N - 7],
1048 s2 = statev[N - 6], s3 = statev[N - 5],
1049 r0 = statev[N - 4], r1 = statev[N - 3],
1050 r2 = statev[N - 2], r3 = statev[N - 1];
1051 for (; count; --count) {
1056 }
else if (count < 0)
1057 for (; count; ++count) {
1059 for (; i + M > N;) {
1062 for (; i > 2 * R;) {
1070 #undef SFMT19937_STEP32
1071 #undef SFMT19937_REVSTEP32
1073 #define SFMT19937_STEP64(I, J) { \
1074 internal_type t = statev[I] ^ statev[I] << 8 ^ \
1075 (statev[J] >> 11 & magic0) ^ \
1076 (s0 >> 8 | s1 << 56) ^ (r0 << 18 & mask18); \
1077 s0 = r0; r0 = t & mask; \
1078 t = statev[I + 1] ^ \
1079 (statev[I + 1] << 8 | statev[I] >> 56) ^ \
1080 (statev[J + 1] >> 11 & magic1) ^ \
1081 s1 >> 8 ^ (r1 << 18 & mask18); \
1082 s1 = r1; r1 = t & mask; \
1083 statev[I] = r0; statev[I + 1] = r1; \
1091 #define SFMT19937_REVSTEP64(I, J, K, L) { \
1093 t0 = statev[I] ^ (statev[J] >> 11 & magic0) ^ \
1094 (statev[K] >> 8 | (statev[K + 1] << 56 & mask)) ^ \
1095 (statev[L] << 18 & mask18), \
1096 t1 = statev[I + 1] ^ (statev[J + 1] >> 11 & magic1) ^ \
1097 statev[K + 1] >> 8 ^ (statev[L + 1] << 18 & mask18); \
1099 t1 ^= t0 >> 32 ^ (t1 << 32 & mask); \
1100 t0 ^= t0 << 32 & mask; \
1101 t1 ^= t0 >> 48 ^ (t1 << 16 & mask); \
1102 t0 ^= t0 << 16 & mask; \
1103 statev[I ] = t0 ^ (t0 << 8 & mask); \
1104 statev[I + 1] = t1 ^ t0 >> 56 ^ (t1 << 8 & mask); \
1114 s0 = statev[N - 4], s1 = statev[N - 3],
1115 r0 = statev[N - 2], r1 = statev[N - 1];
1116 for (; count; --count) {
1121 }
else if (count < 0)
1122 for (; count; ++count) {
1124 for (; i + M > N;) {
1127 for (; i > 2 * R;) {
1135 #undef SFMT19937_STEP64
1136 #undef SFMT19937_REVSTEP64
1138 #endif // HAVE_SSE2 and HAVE_ALTIVEC
1143 engine_type inner = (state[0] & PARITY0) ^ (state[1] & PARITY1) ^
1144 (state[2] & PARITY2) ^ (state[3] & PARITY3);
1145 for (
unsigned s = 16; s; s >>= 1)
1146 inner ^= inner >> s;
1147 STATIC_ASSERT(PARITY_LSB < 32 && PARITY0 & 1u << PARITY_LSB,
1148 "inconsistent PARITY_LSB or PARITY0");
1150 if ((inner & 1u) == 0)
1152 state[PARITY_LSB >> 5] ^= engine_type(1u) << (PARITY_LSB & 31u);
1158 engine_type inner = (state[0] & PARITY0) ^ (state[1] & PARITY1);
1159 for (
unsigned s = 32; s; s >>= 1)
1160 inner ^= inner >> s;
1161 STATIC_ASSERT(PARITY_LSB < 64 && PARITY0 & 1u << PARITY_LSB,
1162 "inconsistent PARITY_LSB or PARITY0");
1164 if ((inner & 1u) == 0)
1166 state[PARITY_LSB >> 6] ^= engine_type(1u) << (PARITY_LSB & 63u);
1169 template<
class RandomType>
1174 for (
unsigned i = 0; i < N; ++i) {
1175 engine_t::CheckSum(state[i], c);
1179 throw RandomErr(
"SFMT19937: All-zero state");
1185 #if RANDOMLIB_POWERTABLE
1189 const float RandomPower2::power2[maxpow - minpow + 1] = {
1190 #if RANDOMLIB_LONGDOUBLEPREC > 64
1193 1/1329227995784915872903807060280344576.f,
1194 1/664613997892457936451903530140172288.f,
1195 1/332306998946228968225951765070086144.f,
1196 1/166153499473114484112975882535043072.f,
1197 1/83076749736557242056487941267521536.f,
1198 1/41538374868278621028243970633760768.f,
1199 1/20769187434139310514121985316880384.f,
1200 1/10384593717069655257060992658440192.f,
1201 1/5192296858534827628530496329220096.f,
1202 1/2596148429267413814265248164610048.f,
1203 1/1298074214633706907132624082305024.f,
1204 1/649037107316853453566312041152512.f,
1205 1/324518553658426726783156020576256.f,
1206 1/162259276829213363391578010288128.f,
1207 1/81129638414606681695789005144064.f,
1208 1/40564819207303340847894502572032.f,
1209 1/20282409603651670423947251286016.f,
1210 1/10141204801825835211973625643008.f,
1211 1/5070602400912917605986812821504.f,
1212 1/2535301200456458802993406410752.f,
1213 1/1267650600228229401496703205376.f,
1214 1/633825300114114700748351602688.f,
1215 1/316912650057057350374175801344.f,
1216 1/158456325028528675187087900672.f,
1217 1/79228162514264337593543950336.f,
1218 1/39614081257132168796771975168.f,
1219 1/19807040628566084398385987584.f,
1220 1/9903520314283042199192993792.f,
1221 1/4951760157141521099596496896.f,
1222 1/2475880078570760549798248448.f,
1223 1/1237940039285380274899124224.f,
1224 1/618970019642690137449562112.f,
1225 1/309485009821345068724781056.f,
1226 1/154742504910672534362390528.f,
1227 1/77371252455336267181195264.f,
1228 1/38685626227668133590597632.f,
1229 1/19342813113834066795298816.f,
1230 1/9671406556917033397649408.f,
1231 1/4835703278458516698824704.f,
1232 1/2417851639229258349412352.f,
1233 1/1208925819614629174706176.f,
1234 1/604462909807314587353088.f,
1235 1/302231454903657293676544.f,
1236 1/151115727451828646838272.f,
1237 1/75557863725914323419136.f,
1238 1/37778931862957161709568.f,
1239 1/18889465931478580854784.f,
1240 1/9444732965739290427392.f,
1241 1/4722366482869645213696.f,
1242 1/2361183241434822606848.f,
1243 1/1180591620717411303424.f,
1244 1/590295810358705651712.f,
1245 1/295147905179352825856.f,
1246 1/147573952589676412928.f,
1247 1/73786976294838206464.f,
1248 1/36893488147419103232.f,
1250 1/18446744073709551616.f,
1251 1/9223372036854775808.f,
1252 1/4611686018427387904.f,
1253 1/2305843009213693952.f,
1254 1/1152921504606846976.f,
1255 1/576460752303423488.f,
1256 1/288230376151711744.f,
1257 1/144115188075855872.f,
1258 1/72057594037927936.f,
1259 1/36028797018963968.f,
1260 1/18014398509481984.f,
1261 1/9007199254740992.f,
1262 1/4503599627370496.f,
1263 1/2251799813685248.f,
1264 1/1125899906842624.f,
1265 1/562949953421312.f,
1266 1/281474976710656.f,
1267 1/140737488355328.f,
1368 18014398509481984.f,
1369 36028797018963968.f,
1370 72057594037927936.f,
1371 144115188075855872.f,
1372 288230376151711744.f,
1373 576460752303423488.f,
1374 1152921504606846976.f,
1375 2305843009213693952.f,
1376 4611686018427387904.f,
1377 9223372036854775808.f,
1378 18446744073709551616.f,
1384 template class RandomEngine< MT19937<Random_u32>, MixerMT0<Random_u32> >;
1385 template class RandomEngine< MT19937<Random_u64>, MixerMT0<Random_u64> >;
1386 template class RandomEngine< MT19937<Random_u32>, MixerMT1<Random_u32> >;
1387 template class RandomEngine< MT19937<Random_u64>, MixerMT1<Random_u64> >;
1389 template class RandomEngine< MT19937<Random_u32>, MixerSFMT>;
1390 template class RandomEngine< MT19937<Random_u64>, MixerSFMT>;
1391 template class RandomEngine<SFMT19937<Random_u32>, MixerSFMT>;
1392 template class RandomEngine<SFMT19937<Random_u64>, MixerSFMT>;
1396 template<> RandomCanonical<MRandomGenerator32>
static std::vector< seed_type > SeedVector()
static void SeedToState(const std::vector< RandomSeed::seed_type > &seed, mixer_type state[], unsigned n)
Generate random integers, reals, and booleans.
result_t::type result_type
void Save(std::ostream &os, bool bin=true) const
Header for Random, RandomGenerator.
engine_t::type internal_type
#define SFMT19937_REVSTEP32(I, J, K, L)
static void NormalizeState(engine_type state[])
void StepCount(long long n)
The original MT19937 mixing functionality.
static void SeedToState(const std::vector< RandomSeed::seed_type > &seed, mixer_type state[], unsigned n)
void Load(std::istream &is, bool bin=true)
#define SFMT19937_STEP64(I, J)
Exception handling for RandomLib.
static std::vector< seed_type > StringToVector(const std::string &s)
static void Read32(std::istream &is, bool bin, type &x)
#define STATIC_ASSERT(cond, reason)
void SetCount(long long n)
static void SeedToState(const std::vector< RandomSeed::seed_type > &seed, mixer_type state[], unsigned n)
static void Transition(long long count, internal_type statev[])
static void CheckState(const engine_type state[], Random_u32::type &check)
void Reseed(const std::vector< IntType > &v)
static void NormalizeState(engine_type state[])
static seed_type SeedWord()
static void CheckState(const engine_type state[], Random_u32::type &check)
static void CheckSum(type n, uint32_t &check)
#define MT19937_STEP(I, J, K)
static void Transition(long long count, internal_type statev[])
#define MT19937_REVSTEP(I, J, K)
Uniform random number generator.
static type cast(IntType x)
#define SFMT19937_STEP32(I, J)
std::string SeedString() const
#define SFMT19937_REVSTEP64(I, J, K, L)
engine_t::type internal_type
static void Write32(std::ostream &os, bool bin, int &cnt, type x)