-
Notifications
You must be signed in to change notification settings - Fork 412
Random number generation classes #2793
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Merged
Merged
Changes from all commits
Commits
Show all changes
16 commits
Select commit
Hold shift + click to select a range
fee9c06
add classes for random number generation
soheilshahrouz a5a4485
add RngContainer class
soheilshahrouz e08a55d
virtual destructor for RandomNumberGeneratorInterface
soheilshahrouz 2e760f9
swap M and N values in SpecRandomNumberGenerator
soheilshahrouz 985352e
resolve compilation warnings in specrand.cpp
soheilshahrouz 7d5e8d5
use vtr::RngContainer for switchpoints
soheilshahrouz 34b71d8
add vtr::RngContainer arguments to initial_noc_placement
soheilshahrouz 7ad803d
pass vtr::RngContainer down the function call hierarchy in initial pl…
soheilshahrouz e1c7379
add a reference to vtr::RngContainer in KArmedBanditAgent
soheilshahrouz bb575f6
update move_utils and RL_agent_util with vtr::RngContainer args
soheilshahrouz 3e50497
update move generators with argument of vtr::RngContainer
soheilshahrouz 93ff837
update noc_place_utils with RngContainer args
soheilshahrouz c99b45f
pass RngContainer argument down the call hierarchy in place.cpp
soheilshahrouz e03148a
use RngContainer in cb_metrics.cpp
soheilshahrouz eaf56c0
fix compilation error in test_random.cpp
soheilshahrouz b83c603
use lower case letters for argument names
soheilshahrouz File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,91 +1,67 @@ | ||
#include <cstddef> | ||
|
||
#include "vtr_random.h" | ||
#include "specrand.h" | ||
#include "vtr_util.h" | ||
#include "vtr_error.h" | ||
#include "specrand.h" | ||
|
||
#define CHECK_RAND | ||
|
||
namespace vtr { | ||
/* Portable random number generator defined below. Taken from ANSI C by * | ||
* K & R. Not a great generator, but fast, and good enough for my needs. */ | ||
|
||
constexpr size_t IA = 1103515245u; | ||
constexpr size_t IC = 12345u; | ||
constexpr size_t IM = 2147483648u; | ||
|
||
static RandState random_state = 0; | ||
|
||
/** | ||
* @brief The pseudo-random number generator is initialized using the argument passed as seed. | ||
*/ | ||
void srandom(int seed) { | ||
random_state = (unsigned int)seed; | ||
#ifdef SPEC_CPU | ||
/* SPEC CPU requires a different random number generator */ | ||
spec_init_genrand((unsigned long)seed); | ||
#endif | ||
RandomNumberGenerator::RandomNumberGenerator(int seed) { | ||
random_state_ = (unsigned int)seed; | ||
} | ||
|
||
/* returns the random_state value */ | ||
RandState get_random_state() { | ||
return random_state; | ||
RandomNumberGenerator::RandomNumberGenerator() | ||
: RandomNumberGenerator(0) {} | ||
|
||
void RandomNumberGenerator::srandom(int seed) { | ||
random_state_ = (unsigned int)seed; | ||
} | ||
|
||
int irand(int imax, RandState& state) { | ||
#ifdef SPEC_CPU | ||
/* SPEC CPU requires a different random number generator */ | ||
return (int)(spec_genrand_int31() % (imax + 1)); | ||
#else | ||
/* Creates a random integer between 0 and imax, inclusive. i.e. [0..imax] */ | ||
int RandomNumberGenerator::irand(int imax) { | ||
// Creates a random integer between 0 and imax, inclusive. i.e. [0..imax] | ||
int ival; | ||
|
||
/* state = (state * IA + IC) % IM; */ | ||
state = state * IA + IC; /* Use overflow to wrap */ | ||
ival = state & (IM - 1); /* Modulus */ | ||
// state = (state * IA + IC) % IM; | ||
random_state_ = random_state_ * IA + IC; // Use overflow to wrap | ||
ival = random_state_ & (IM - 1); // Modulus | ||
ival = (int)((float)ival * (float)(imax + 0.999) / (float)IM); | ||
|
||
# ifdef CHECK_RAND | ||
if ((ival < 0) || (ival > imax)) { | ||
if (ival == imax + 1) { | ||
/* Due to random floating point rounding, sometimes above calculation gives number greater than ival by 1 */ | ||
ival = imax; | ||
} else { | ||
throw VtrError(string_fmt("Bad value in my_irand, imax = %d ival = %d", imax, ival), __FILE__, __LINE__); | ||
if constexpr (CHECK_RAND_CONSTEXPR) { | ||
if ((ival < 0) || (ival > imax)) { | ||
if (ival == imax + 1) { | ||
// Due to random floating point rounding, sometimes above calculation gives number greater than ival by 1 | ||
ival = imax; | ||
} else { | ||
throw VtrError(string_fmt("Bad value in my_irand, imax = %d ival = %d", imax, ival), __FILE__, __LINE__); | ||
} | ||
} | ||
} | ||
# endif | ||
|
||
return ival; | ||
#endif | ||
} | ||
|
||
int irand(int imax) { | ||
return irand(imax, random_state); | ||
} | ||
float RandomNumberGenerator::frand() { | ||
random_state_ = random_state_ * IA + IC; /* Use overflow to wrap */ | ||
int ival = random_state_ & (IM - 1); /* Modulus */ | ||
float fval = (float)ival / (float)IM; | ||
|
||
float frand() { | ||
/* Creates a random float between 0 and 1. i.e. [0..1). */ | ||
#ifdef SPEC_CPU | ||
/* SPEC CPU requires a different random number generator */ | ||
return (float)spec_genrand_real2(); | ||
#else | ||
float fval; | ||
int ival; | ||
if constexpr (CHECK_RAND_CONSTEXPR) { | ||
if (fval < 0 || fval > 1.) { | ||
throw VtrError(string_fmt("Bad value in my_frand, fval = %g", fval), __FILE__, __LINE__); | ||
} | ||
} | ||
|
||
random_state = random_state * IA + IC; /* Use overflow to wrap */ | ||
ival = random_state & (IM - 1); /* Modulus */ | ||
fval = (float)ival / (float)IM; | ||
return fval; | ||
} | ||
|
||
# ifdef CHECK_RAND | ||
if ((fval < 0) || (fval > 1.)) { | ||
throw VtrError(string_fmt("Bad value in my_frand, fval = %g", fval), __FILE__, __LINE__); | ||
RngContainer::RngContainer(int seed) { | ||
if constexpr (SPEC_CPU_CONSTEXPR) { | ||
rng_ = std::make_unique<SpecRandomNumberGenerator>(seed); | ||
} else { | ||
rng_ = std::make_unique<vtr::RandomNumberGenerator>(seed); | ||
} | ||
# endif | ||
|
||
return (fval); | ||
#endif | ||
} | ||
|
||
RngContainer::RngContainer() | ||
: RngContainer(0) {} | ||
} // namespace vtr |
Oops, something went wrong.
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Could/should we just use the SPEC random number generator all the time? I put in the original random number generator, but if the SPEC one has better randomness and isn't noticeably slower we could just make these routines call it.
I don't have a really strong opinion about this, but maybe we can simplify a code path.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I am concerned that if we use SPEC random generator, we need to update golden results for a large number of tests. We can explore the performance/quality trade-off of these two random generators later.