#include <random_generator.hpp>
Public Member Functions | |
RandomGenerator () | |
~RandomGenerator () | |
int | srand (int x=0) |
int | rand () |
int | rand (int v) |
int | rand (int u, int v) |
double | randf (double v) |
double | randf (double u, double v) |
int | rand1i (int v) |
int | rand2i (int u, int v) |
float | rand1f (float v) |
float | rand2f (float u, float v) |
void | initialize () |
void | srandom (unsigned long x) |
long | random () |
Private Member Functions | |
RandomGenerator (const RandomGenerator &) | |
RandomGenerator & | operator= (const RandomGenerator &) |
Private Attributes | |
bool | initialized |
long | degrees [MAX_TYPES] |
long | seps [MAX_TYPES] |
long | randtbl [DEG_3+1] |
long * | fptr |
long * | rptr |
long * | state |
long | rand_type |
long | rand_deg |
long | rand_sep |
long * | end_ptr |
int | debug |
Static Private Attributes | |
static const int | TYPE_0 = 0 |
static const int | BREAK_0 = 8 |
static const int | DEG_0 = 0 |
static const int | SEP_0 = 0 |
static const int | TYPE_1 = 1 |
static const int | BREAK_1 = 32 |
static const int | DEG_1 = 7 |
static const int | SEP_1 = 3 |
static const int | TYPE_2 = 2 |
static const int | BREAK_2 = 64 |
static const int | DEG_2 = 15 |
static const int | SEP_2 = 1 |
static const int | TYPE_3 = 3 |
static const int | BREAK_3 = 128 |
static const int | DEG_3 = 31 |
static const int | SEP_3 = 3 |
static const int | TYPE_4 = 4 |
static const int | BREAK_4 = 256 |
static const int | DEG_4 = 63 |
static const int | SEP_4 = 1 |
static const int | MAX_TYPES = 5 |
static const int | rand_max = 0x7fffffff |
Definition at line 37 of file random_generator.hpp.
RandomGenerator::RandomGenerator | ( | ) |
Definition at line 47 of file random_generator.cpp.
References debug, initialize(), and initialized.
00047 : 00048 initialized(), 00049 fptr(), 00050 rptr(), 00051 state(), 00052 rand_type(), 00053 rand_deg(), 00054 rand_sep(), 00055 end_ptr(), 00056 debug() 00057 { 00058 assert(sizeof(int) >= 4); 00059 initialized = 0; 00060 debug = 0; // change this by hand for debug 00061 initialize(); 00062 }
RandomGenerator::~RandomGenerator | ( | ) |
RandomGenerator::RandomGenerator | ( | const RandomGenerator & | ) | [private] |
int RandomGenerator::srand | ( | int | x = 0 |
) |
Definition at line 67 of file random_generator.cpp.
References debug, rand_max, and srandom().
Referenced by Main::init_rand(), scripting::play_demo(), and GameSession::restart_level().
00067 { 00068 int x0 = x; 00069 while (x <= 0) // random seed of zero means 00070 x = time(0) % RandomGenerator::rand_max; // randomize with time 00071 00072 if (debug > 0) 00073 printf("==== srand(%10d) (%10d) rand_max=%x =====\n", 00074 x, x0, RandomGenerator::rand_max); 00075 00076 RandomGenerator::srandom(x); 00077 return x; // let caller know seed used 00078 }
int RandomGenerator::rand | ( | ) |
Definition at line 80 of file random_generator.cpp.
References debug, and random().
Referenced by Stalactite::active_update(), Kugelblitz::active_update(), CloudParticleSystem::CloudParticleSystem(), CometParticleSystem::CometParticleSystem(), SkullTile::draw(), Candle::draw(), BrokenBrick::draw(), get_random_color(), GhostParticleSystem::GhostParticleSystem(), Kugelblitz::hit(), Dispenser::launch_badguy(), Particles::Particles(), RainParticleSystem::RainParticleSystem(), scripting::rand(), rand(), rand1i(), rand2i(), GameSession::restart_level(), SnowParticleSystem::SnowParticleSystem(), Mole::throw_rock(), Wind::update(), RainParticleSystem::update(), Player::update(), GhostParticleSystem::update(), CometParticleSystem::update(), and Zeekling::Zeekling().
00080 { 00081 int rv; // a positive int 00082 while ((rv = RandomGenerator::random()) <= 0) // neg or zero causes probs 00083 ; 00084 if (debug > 0) 00085 printf("==== rand(): %10d =====\n", rv); 00086 return rv; 00087 }
int RandomGenerator::rand | ( | int | v | ) |
Definition at line 89 of file random_generator.cpp.
References rand_max, and random().
00089 { 00090 assert(v >= 0 && v <= RandomGenerator::rand_max); // illegal arg 00091 00092 // remove biases, esp. when v is large (e.g. v == (rand_max/4)*3;) 00093 int rv, maxV =(RandomGenerator::rand_max / v) * v; 00094 assert(maxV <= RandomGenerator::rand_max); 00095 while ((rv = RandomGenerator::random()) >= maxV) 00096 ; 00097 return rv % v; // mod it down to 0..(maxV-1) 00098 }
int RandomGenerator::rand | ( | int | u, | |
int | v | |||
) |
Definition at line 100 of file random_generator.cpp.
References rand().
00100 { 00101 assert(v > u); 00102 return u + RandomGenerator::rand(v-u); 00103 }
double RandomGenerator::randf | ( | double | v | ) |
Definition at line 105 of file random_generator.cpp.
References debug, rand_max, and random().
Referenced by FlyingSnowBall::activate(), GhostTree::active_update(), FlyingSnowBall::active_update(), CloudParticleSystem::CloudParticleSystem(), Firefly::collision(), Stumpy::collision_squished(), PoisonIvy::collision_squished(), MrTree::collision_squished(), CometParticleSystem::CometParticleSystem(), Explosion::explode(), GhostParticleSystem::GhostParticleSystem(), LevelIntro::LevelIntro(), PulsingLight::PulsingLight(), RainParticleSystem::RainParticleSystem(), rand1f(), rand2f(), randf(), SkullyHop::set_state(), SnowParticleSystem::SnowParticleSystem(), LevelIntro::update(), Wind::update(), SnowParticleSystem::update(), Player::update(), and Fireworks::update().
00105 { 00106 float rv; 00107 do { 00108 rv = ((double)RandomGenerator::random())/RandomGenerator::rand_max * v; 00109 } while (rv >= v); // rounding might cause rv==v 00110 00111 if (debug > 0) 00112 printf("==== rand(): %f =====\n", rv); 00113 return rv; 00114 }
double RandomGenerator::randf | ( | double | u, | |
double | v | |||
) |
Definition at line 116 of file random_generator.cpp.
References randf().
00116 { 00117 return u + RandomGenerator::randf(v-u); 00118 }
int RandomGenerator::rand1i | ( | int | v | ) | [inline] |
int RandomGenerator::rand2i | ( | int | u, | |
int | v | |||
) | [inline] |
float RandomGenerator::rand1f | ( | float | v | ) | [inline] |
Definition at line 110 of file random_generator.hpp.
References randf().
00111 { return static_cast<float>(randf(static_cast<double>(v))); }
float RandomGenerator::rand2f | ( | float | u, | |
float | v | |||
) | [inline] |
Definition at line 112 of file random_generator.hpp.
References randf().
00113 { return static_cast<float>(randf(static_cast<double>(u), 00114 static_cast<double>(v))); }
void RandomGenerator::initialize | ( | ) |
Definition at line 200 of file random_generator.cpp.
References DEG_0, DEG_1, DEG_2, DEG_3, DEG_4, degrees, end_ptr, fptr, rand_deg, rand_sep, rand_type, randtbl, rptr, SEP_0, SEP_1, SEP_2, SEP_3, SEP_4, seps, state, and TYPE_3.
Referenced by RandomGenerator().
00200 { 00201 00202 #define NSHUFF 100 // To drop part of seed -> 1st value correlation 00203 00204 //static long degrees[MAX_TYPES] = { DEG_0, DEG_1, DEG_2, DEG_3, DEG_4 }; 00205 //static long seps [MAX_TYPES] = { SEP_0, SEP_1, SEP_2, SEP_3, SEP_4 }; 00206 00207 degrees[0] = DEG_0; 00208 degrees[1] = DEG_1; 00209 degrees[2] = DEG_2; 00210 degrees[3] = DEG_3; 00211 degrees[4] = DEG_4; 00212 00213 seps [0] = SEP_0; 00214 seps [1] = SEP_1; 00215 seps [2] = SEP_2; 00216 seps [3] = SEP_3; 00217 seps [4] = SEP_4; 00218 00219 // 00220 // Initially, everything is set up as if from: 00221 // 00222 // initstate(1, randtbl, 128); 00223 // 00224 // Note that this initialization takes advantage of the fact that srandom() 00225 // advances the front and rear pointers 10*rand_deg times, and hence the 00226 // rear pointer which starts at 0 will also end up at zero; thus the zeroeth 00227 // element of the state information, which contains info about the current 00228 // position of the rear pointer is just 00229 // 00230 // MAX_TYPES * (rptr - state) + TYPE_3 == TYPE_3. 00231 00232 randtbl[ 0] = TYPE_3; 00233 randtbl[ 1] = 0x991539b1; 00234 randtbl[ 2] = 0x16a5bce3; 00235 randtbl[ 3] = 0x6774a4cd; 00236 randtbl[ 4] = 0x3e01511e; 00237 randtbl[ 5] = 0x4e508aaa; 00238 randtbl[ 6] = 0x61048c05; 00239 randtbl[ 7] = 0xf5500617; 00240 randtbl[ 8] = 0x846b7115; 00241 randtbl[ 9] = 0x6a19892c; 00242 randtbl[10] = 0x896a97af; 00243 randtbl[11] = 0xdb48f936; 00244 randtbl[12] = 0x14898454; 00245 randtbl[13] = 0x37ffd106; 00246 randtbl[14] = 0xb58bff9c; 00247 randtbl[15] = 0x59e17104; 00248 randtbl[16] = 0xcf918a49; 00249 randtbl[17] = 0x09378c83; 00250 randtbl[18] = 0x52c7a471; 00251 randtbl[19] = 0x8d293ea9; 00252 randtbl[20] = 0x1f4fc301; 00253 randtbl[21] = 0xc3db71be; 00254 randtbl[22] = 0x39b44e1c; 00255 randtbl[23] = 0xf8a44ef9; 00256 randtbl[24] = 0x4c8b80b1; 00257 randtbl[25] = 0x19edc328; 00258 randtbl[26] = 0x87bf4bdd; 00259 randtbl[27] = 0xc9b240e5; 00260 randtbl[28] = 0xe9ee4b1b; 00261 randtbl[29] = 0x4382aee7; 00262 randtbl[30] = 0x535b6b41; 00263 randtbl[31] = 0xf3bec5da; 00264 00265 // static long randtbl[DEG_3 + 1] = 00266 // { 00267 // TYPE_3; 00268 // 0x991539b1, 0x16a5bce3, 0x6774a4cd, 0x3e01511e, 0x4e508aaa, 0x61048c05, 00269 // 0xf5500617, 0x846b7115, 0x6a19892c, 0x896a97af, 0xdb48f936, 0x14898454, 00270 // 0x37ffd106, 0xb58bff9c, 0x59e17104, 0xcf918a49, 0x09378c83, 0x52c7a471, 00271 // 0x8d293ea9, 0x1f4fc301, 0xc3db71be, 0x39b44e1c, 0xf8a44ef9, 0x4c8b80b1, 00272 // 0x19edc328, 0x87bf4bdd, 0xc9b240e5, 0xe9ee4b1b, 0x4382aee7, 0x535b6b41, 00273 // 0xf3bec5da 00274 // }; 00275 00276 // 00277 // fptr and rptr are two pointers into the state info, a front and a rear 00278 // pointer. These two pointers are always rand_sep places aparts, as they 00279 // cycle cyclically through the state information. (Yes, this does mean we 00280 // could get away with just one pointer, but the code for random() is more 00281 // efficient this way). The pointers are left positioned as they would be 00282 // from the call 00283 // 00284 // initstate(1, randtbl, 128); 00285 // 00286 // (The position of the rear pointer, rptr, is really 0 (as explained above 00287 // in the initialization of randtbl) because the state table pointer is set 00288 // to point to randtbl[1] (as explained below). 00289 // 00290 00291 fptr = &randtbl[SEP_3 + 1]; 00292 rptr = &randtbl[1]; 00293 00294 // 00295 // The following things are the pointer to the state information table, the 00296 // type of the current generator, the degree of the current polynomial being 00297 // used, and the separation between the two pointers. Note that for efficiency 00298 // of random(), we remember the first location of the state information, not 00299 // the zeroeth. Hence it is valid to access state[-1], which is used to 00300 // store the type of the R.N.G. Also, we remember the last location, since 00301 // this is more efficient than indexing every time to find the address of 00302 // the last element to see if the front and rear pointers have wrapped. 00303 // 00304 00305 state = &randtbl[1]; 00306 rand_type = TYPE_3; 00307 rand_deg = DEG_3; 00308 rand_sep = SEP_3; 00309 end_ptr = &randtbl[DEG_3 + 1]; 00310 00311 }
void RandomGenerator::srandom | ( | unsigned long | x | ) |
Definition at line 347 of file random_generator.cpp.
References fptr, good_rand(), initialized, NSHUFF, rand_deg, rand_sep, rand_type, random(), rptr, state, and TYPE_0.
Referenced by srand().
00348 { 00349 long i, lim; 00350 00351 state[0] = x; 00352 if (rand_type == TYPE_0) 00353 lim = NSHUFF; 00354 else 00355 { 00356 for (i = 1; i < rand_deg; i++) state[i] = good_rand(state[i - 1]); 00357 fptr = &state[rand_sep]; 00358 rptr = &state[0]; 00359 lim = 10 * rand_deg; 00360 } 00361 00362 initialized = 1; 00363 for (i = 0; i < lim; i++) random(); 00364 }
long RandomGenerator::random | ( | ) |
Definition at line 564 of file random_generator.cpp.
References end_ptr, fptr, good_rand(), initialized, rand_type, rptr, and TYPE_0.
Referenced by rand(), randf(), and srandom().
00565 { 00566 long i; 00567 long *f, *r; 00568 if (!initialized) { 00569 throw std::runtime_error("uninitialized RandomGenerator object"); 00570 } 00571 00572 if (rand_type == TYPE_0) 00573 { 00574 i = state[0]; 00575 state[0] = i = (good_rand(i)) & 0x7fffffff; 00576 } 00577 else 00578 { 00579 f = fptr; r = rptr; 00580 *f += *r; 00581 i = (*f >> 1) & 0x7fffffff; // Chucking least random bit 00582 if (++f >= end_ptr) 00583 { 00584 f = state; 00585 ++r; 00586 } 00587 else if (++r >= end_ptr) 00588 r = state; 00589 00590 fptr = f; rptr = r; 00591 } 00592 00593 return i; 00594 }
RandomGenerator& RandomGenerator::operator= | ( | const RandomGenerator & | ) | [private] |
const int RandomGenerator::TYPE_0 = 0 [static, private] |
const int RandomGenerator::BREAK_0 = 8 [static, private] |
Definition at line 43 of file random_generator.hpp.
const int RandomGenerator::DEG_0 = 0 [static, private] |
const int RandomGenerator::SEP_0 = 0 [static, private] |
const int RandomGenerator::TYPE_1 = 1 [static, private] |
Definition at line 47 of file random_generator.hpp.
const int RandomGenerator::BREAK_1 = 32 [static, private] |
Definition at line 48 of file random_generator.hpp.
const int RandomGenerator::DEG_1 = 7 [static, private] |
const int RandomGenerator::SEP_1 = 3 [static, private] |
const int RandomGenerator::TYPE_2 = 2 [static, private] |
Definition at line 52 of file random_generator.hpp.
const int RandomGenerator::BREAK_2 = 64 [static, private] |
Definition at line 53 of file random_generator.hpp.
const int RandomGenerator::DEG_2 = 15 [static, private] |
const int RandomGenerator::SEP_2 = 1 [static, private] |
const int RandomGenerator::TYPE_3 = 3 [static, private] |
const int RandomGenerator::BREAK_3 = 128 [static, private] |
Definition at line 58 of file random_generator.hpp.
const int RandomGenerator::DEG_3 = 31 [static, private] |
const int RandomGenerator::SEP_3 = 3 [static, private] |
const int RandomGenerator::TYPE_4 = 4 [static, private] |
Definition at line 62 of file random_generator.hpp.
const int RandomGenerator::BREAK_4 = 256 [static, private] |
Definition at line 63 of file random_generator.hpp.
const int RandomGenerator::DEG_4 = 63 [static, private] |
const int RandomGenerator::SEP_4 = 1 [static, private] |
const int RandomGenerator::MAX_TYPES = 5 [static, private] |
Definition at line 67 of file random_generator.hpp.
bool RandomGenerator::initialized [private] |
Definition at line 69 of file random_generator.hpp.
Referenced by random(), RandomGenerator(), and srandom().
long RandomGenerator::degrees[MAX_TYPES] [private] |
long RandomGenerator::seps[MAX_TYPES] [private] |
long RandomGenerator::randtbl[DEG_3+1] [private] |
long* RandomGenerator::fptr [private] |
Definition at line 74 of file random_generator.hpp.
Referenced by initialize(), random(), and srandom().
long* RandomGenerator::rptr [private] |
Definition at line 75 of file random_generator.hpp.
Referenced by initialize(), random(), and srandom().
long* RandomGenerator::state [private] |
long RandomGenerator::rand_type [private] |
Definition at line 78 of file random_generator.hpp.
Referenced by initialize(), random(), and srandom().
long RandomGenerator::rand_deg [private] |
long RandomGenerator::rand_sep [private] |
long* RandomGenerator::end_ptr [private] |
int RandomGenerator::debug [private] |
Definition at line 82 of file random_generator.hpp.
Referenced by rand(), randf(), RandomGenerator(), and srand().
const int RandomGenerator::rand_max = 0x7fffffff [static, private] |