#include "Random.h" #include "Zeit.h" #include using namespace Framework; RandomGenerator::RandomGenerator() : ReferenceCounter() { int tmp[] = { 3, -1726662223, 379960547, 1735697613, 1040273694, 1313901226, 1627687941, -179304937, -2073333483, 1780058412, -1989503057, -615974602, 344556628, 939512070, -1249116260, 1507946756, -812545463, 154635395, 1388815473, -1926676823, 525320961, -1009028674, 968117788, -123449607, 1284210865, 435012392, -2017506339, -911064859, -370259173, 1132637927, 1398500161, -205601318, }; memcpy( randtbl, tmp, 32 * 4 ); unsafe_state = { &randtbl[ 4 ], &randtbl[ 1 ], &randtbl[ 1 ], 3, 31, 3, &randtbl[ 32 ] }; offset = 0; srand( (int)time( 0 ) ); } // Destruktor RandomGenerator::~RandomGenerator() {} void RandomGenerator::srand( int seed ) { this->seed = seed; int type; int *state; long int i; int word; int *dst; int kc; type = unsafe_state.rand_type; if( (unsigned int)type >= 5 ) return; state = unsafe_state.state; if( seed == 0 ) seed = 1; state[ 0 ] = seed; if( type == 0 ) return; dst = state; word = seed; kc = unsafe_state.rand_deg; for( i = 1; i < kc; ++i ) { long int hi = word / 127773; long int lo = word % 127773; word = (int)( 16807 * lo - 2836 * hi ); if( word < 0 ) word += 2147483647; *++dst = word; } unsafe_state.fptr = &state[ unsafe_state.rand_sep ]; unsafe_state.rptr = &state[ 0 ]; kc *= 10; while( --kc >= 0 ) rand(); } void RandomGenerator::setSeed( __int64 seed ) { this->offset = 0; int offset = (int)( seed >> 32 ); srand( (int)seed ); offset -= this->offset; while( offset-- > 0 ) rand(); } double RandomGenerator::rand() { offset++; int *state; state = unsafe_state.state; if( unsafe_state.rand_type == 0 ) { int val = state[ 0 ]; val = ( ( state[ 0 ] * 1103515245 ) + 12345 ) & 0x7fffffff; state[ 0 ] = val; return val / 2147483647.0; } else { int *fptr = unsafe_state.fptr; int *rptr = unsafe_state.rptr; int *end_ptr = unsafe_state.end_ptr; int val; val = *fptr += *rptr; int result = ( val >> 1 ) & 0x7fffffff; ++fptr; if( fptr >= end_ptr ) { fptr = state; ++rptr; } else { ++rptr; if( rptr >= end_ptr ) rptr = state; } unsafe_state.fptr = fptr; unsafe_state.rptr = rptr; double res = result / 2147483647.0; return res; } return 0; } __int64 RandomGenerator::getSeed() const { __int64 ret = ( (__int64)offset << 32 ) | seed; return ret; }