-
Notifications
You must be signed in to change notification settings - Fork 759
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
Partial rng replace #2084
base: master
Are you sure you want to change the base?
Partial rng replace #2084
Conversation
…nto partial_rng_replace
|
||
int32_t GetRndSeedV2() | ||
{ | ||
std::uniform_int_distribution<int32_t> dist(0, INT_MAX); |
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.
Using the default constructor here has the same effect, creating a distribution with a lower bound of 0 and upper bound of std::numeric_limits<int32_t>::max().
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.
dunno, I tested and the results were off by 1
{ | ||
if (v <= 0) | ||
return 0; | ||
return GetRndSeedV2() % v; |
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.
Given you're using std::uniform_int_distribution why not use distribution params with v-1 as the max? This would also let you avoid modulo bias, fitting into the stated goal of improving randomness. v-1
would be necessary as std::uniform_int_distribution uses a closed interval but the existing GenerateRnd function uses a half-open interval.
You could also simplify call sites that use a lower bound (weapon damage rolls for example) by providing an overload with a minimum bound parameter. If dist was created and stored alongside rng with the default distribution then something like the following would be suitable for bounded random number generation:
int32_t GenerateRndV2(int32_t max, int32_t min)
{
if (max <= min)
return min;
return dist(rng, std::uniform_int_distribution<int32_t>::param_type{ min, max });
}
These callers currently add 1 to the argument to account for GenerateRnd's half-open interval, an approach like this would make that no longer necessary.
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.
it's not the goal of this PR
@@ -2324,19 +2325,19 @@ bool PlrHitMonst(int pnum, int m) | |||
if (hit < hper) { | |||
#endif | |||
if (player._pIFlags & ISPL_FIREDAM && player._pIFlags & ISPL_LIGHTDAM) { | |||
int midam = player._pIFMinDam + GenerateRnd(player._pIFMaxDam - player._pIFMinDam); | |||
int midam = player._pIFMinDam + GenerateRndV2(player._pIFMaxDam - player._pIFMinDam); |
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.
Highest value this can generate is player._pIFMaxDam - 1
, is this a pre-existing bug?
@@ -2733,7 +2734,7 @@ bool PM_DoRangeAttack(int pnum) | |||
mistype = MIS_LARROW; | |||
} | |||
if ((player._pIFlags & ISPL_FIRE_ARROWS) != 0 && (player._pIFlags & ISPL_LIGHT_ARROWS) != 0) { | |||
dmg = player._pIFMinDam + GenerateRnd(player._pIFMaxDam - player._pIFMinDam); | |||
dmg = player._pIFMinDam + GenerateRndV2(player._pIFMaxDam - player._pIFMinDam); |
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.
Same potential (existing) bug here, damage range is [min, max)
Is this algo guaranteed to give the same sequence when setting the same seed? |
std::mt19937 is a default set of arguments for the mersenne twister engine, Running a quick test shows that calling the distribution with different params doesn't affect the generator, and a uniform_int_distribution appears to be consistent for the same generator values. In the following output all three lines were generated with the default mt19937 seed and a distribution having a default interval of [0, 100].
The same numbers were generated in the same order, and mapped to the same output for a given interval even when the distribution params varied between runs (cols 3-6 for example). |
My biggest worry is that there could be a difference between two std implementations, but sounds like it's part of the spec to be stable. |
obviously |
vanilla rng
|
my rng
|
tested with https://github.com/dj-on-github/sp800_22_tests These numbers don't mean much but there were many rng flaws that could be observed during actual gameplay - stat shrine boosted dex 90% of the time etc. that's why one of the shrines even has "favors shields" in description. That's just poo rng. |
…ators This builds on the work done by qndel in diasurgical#2084. I have not updated any of the call sites identified in that PR as I wanted to make it obvious that this does not change existing code. This is more of a discussion point at the moment. I was thinking that namespaces would be a good way to delineate behaviour. I've implemented "vanilla" to cover the base game logic and bugs. "randomV1" is based on diasurgical#2084 and uses STL concepts to add convenience functions as discussed in diasurgical#2193. The API design is intended to be common between versions. The next step would be to update the vanilla namespace functions to align member functions of vanilla::RandomEngine. The reason for having this class is to allow creating a RandomEngine object and passing it in to the level/item generation code (for example) to make it clearer how a given object/dungeon layout is generated. Looking at code such as quests.cpp:165 makes me think a "vanillaSafe" namespace which fixes the negative number bug would be useful, but this would be a future enhancement iff this proposal is acceptable.
…ators This builds on the work done by qndel in diasurgical#2084. I have not updated any of the call sites identified in that PR as I wanted to make it obvious that this does not change existing code. This is more of a discussion point at the moment. I was thinking that namespaces would be a good way to delineate behaviour. I've implemented "vanilla" to cover the base game logic and bugs. "randomV1" is based on diasurgical#2084 and uses STL concepts to add convenience functions as discussed in diasurgical#2193. The API design is intended to be common between versions. The next step would be to update the vanilla namespace functions to align member functions of vanilla::RandomEngine. The reason for having this class is to allow creating a RandomEngine object and passing it in to the level/item generation code (for example) to make it clearer how a given object/dungeon layout is generated. Looking at code such as quests.cpp:165 makes me think a "vanillaSafe" namespace which fixes the negative number bug would be useful, but this would be a future enhancement iff this proposal is acceptable.
…ators This builds on the work done by qndel in diasurgical#2084. I have not updated any of the call sites identified in that PR as I wanted to make it obvious that this does not change existing code. This is more of a discussion point at the moment. I was thinking that namespaces would be a good way to delineate behaviour. I've implemented "vanilla" to cover the base game logic and bugs. "randomV1" is based on diasurgical#2084 and uses STL concepts to add convenience functions as discussed in diasurgical#2193. The API design is intended to be common between versions. The next step would be to update the vanilla namespace functions to align member functions of vanilla::RandomEngine. The reason for having this class is to allow creating a RandomEngine object and passing it in to the level/item generation code (for example) to make it clearer how a given object/dungeon layout is generated. Looking at code such as quests.cpp:165 makes me think a "vanillaSafe" namespace which fixes the negative number bug would be useful, but this would be a future enhancement iff this proposal is acceptable.
…ators This builds on the work done by qndel in diasurgical#2084. I have not updated any of the call sites identified in that PR as I wanted to make it obvious that this does not change existing code. This is more of a discussion point at the moment. I was thinking that namespaces would be a good way to delineate behaviour. I've implemented "vanilla" to cover the base game logic and bugs. "randomV1" is based on diasurgical#2084 and uses STL concepts to add convenience functions as discussed in diasurgical#2193. The API design is intended to be common between versions. The next step would be to update the vanilla namespace functions to align member functions of vanilla::RandomEngine. The reason for having this class is to allow creating a RandomEngine object and passing it in to the level/item generation code (for example) to make it clearer how a given object/dungeon layout is generated. Looking at code such as quests.cpp:165 makes me think a "vanillaSafe" namespace which fixes the negative number bug would be useful, but this would be a future enhancement iff this proposal is acceptable.
…ators This builds on the work done by qndel in diasurgical#2084. I have not updated any of the call sites identified in that PR as I wanted to make it obvious that this does not change existing code. This is more of a discussion point at the moment. I was thinking that namespaces would be a good way to delineate behaviour. I've implemented "vanilla" to cover the base game logic and bugs. "randomV1" is based on diasurgical#2084 and uses STL concepts to add convenience functions as discussed in diasurgical#2193. The API design is intended to be common between versions. The next step would be to update the vanilla namespace functions to align member functions of vanilla::RandomEngine. The reason for having this class is to allow creating a RandomEngine object and passing it in to the level/item generation code (for example) to make it clearer how a given object/dungeon layout is generated. Looking at code such as quests.cpp:165 makes me think a "vanillaSafe" namespace which fixes the negative number bug would be useful, but this would be a future enhancement iff this proposal is acceptable.
…ators This builds on the work done by qndel in diasurgical#2084. I have not updated any of the call sites identified in that PR as I wanted to make it obvious that this does not change existing code. This is more of a discussion point at the moment. I was thinking that namespaces would be a good way to delineate behaviour. I've implemented "vanilla" to cover the base game logic and bugs. "randomV1" is based on diasurgical#2084 and uses STL concepts to add convenience functions as discussed in diasurgical#2193. The API design is intended to be common between versions. The next step would be to update the vanilla namespace functions to align member functions of vanilla::RandomEngine. The reason for having this class is to allow creating a RandomEngine object and passing it in to the level/item generation code (for example) to make it clearer how a given object/dungeon layout is generated. Looking at code such as quests.cpp:165 makes me think a "vanillaSafe" namespace which fixes the negative number bug would be useful, but this would be a future enhancement iff this proposal is acceptable.
…ators This builds on the work done by qndel in diasurgical#2084. I have not updated any of the call sites identified in that PR as I wanted to make it obvious that this does not change existing code. This is more of a discussion point at the moment. I was thinking that namespaces would be a good way to delineate behaviour. I've implemented "vanilla" to cover the base game logic and bugs. "randomV1" is based on diasurgical#2084 and uses STL concepts to add convenience functions as discussed in diasurgical#2193. The API design is intended to be common between versions. The next step would be to update the vanilla namespace functions to align member functions of vanilla::RandomEngine. The reason for having this class is to allow creating a RandomEngine object and passing it in to the level/item generation code (for example) to make it clearer how a given object/dungeon layout is generated. Looking at code such as quests.cpp:165 makes me think a "vanillaSafe" namespace which fixes the negative number bug would be useful, but this would be a future enhancement iff this proposal is acceptable.
…ators This builds on the work done by qndel in diasurgical#2084. I have not updated any of the call sites identified in that PR as I wanted to make it obvious that this does not change existing code. This is more of a discussion point at the moment. I was thinking that namespaces would be a good way to delineate behaviour. I've implemented "vanilla" to cover the base game logic and bugs. "randomV1" is based on diasurgical#2084 and uses STL concepts to add convenience functions as discussed in diasurgical#2193. The API design is intended to be common between versions. The next step would be to update the vanilla namespace functions to align with member functions of vanilla::RandomEngine. The reason for having this class is to allow creating a RandomEngine object and passing it in to the level/item generation code (for example) to make it clearer how a given object/dungeon layout is generated. Looking at code such as quests.cpp:165 makes me think a "vanillaSafe" namespace which fixes the negative number bug would be useful, but this would be a future enhancement iff this proposal is acceptable. Add libgmock-dev to the install script for linux_x86_64_test to use EXPECT_THAT and ::testing::AnyOf
…ators This builds on the work done by qndel in diasurgical#2084. I have not updated any of the call sites identified in that PR as I wanted to make it obvious that this does not change existing code. This is more of a discussion point at the moment. I was thinking that namespaces would be a good way to delineate behaviour. I've implemented "vanilla" to cover the base game logic and bugs. "randomV1" is based on diasurgical#2084 and uses STL concepts to add convenience functions as discussed in diasurgical#2193. The API design is intended to be common between versions. The next step would be to update the vanilla namespace functions to align with member functions of vanilla::RandomEngine. The reason for having this class is to allow creating a RandomEngine object and passing it in to the level/item generation code (for example) to make it clearer how a given object/dungeon layout is generated. Looking at code such as quests.cpp:165 makes me think a "vanillaSafe" namespace which fixes the negative number bug would be useful, but this would be a future enhancement iff this proposal is acceptable. Add libgmock-dev to the install script for linux_x86_64_test to use EXPECT_THAT and ::testing::AnyOf
…ators This builds on the work done by qndel in diasurgical#2084. I have not updated any of the call sites identified in that PR as I wanted to make it obvious that this does not change existing code. This is more of a discussion point at the moment. I was thinking that namespaces would be a good way to delineate behaviour. I've implemented "vanilla" to cover the base game logic and bugs. "randomV1" is based on diasurgical#2084 and uses STL concepts to add convenience functions as discussed in diasurgical#2193. The API design is intended to be common between versions. The next step would be to update the vanilla namespace functions to align with member functions of vanilla::RandomEngine. The reason for having this class is to allow creating a RandomEngine object and passing it in to the level/item generation code (for example) to make it clearer how a given object/dungeon layout is generated. Looking at code such as quests.cpp:165 makes me think a "vanillaSafe" namespace which fixes the negative number bug would be useful, but this would be a future enhancement iff this proposal is acceptable. Add libgmock-dev to the install script for linux_x86_64_test to use EXPECT_THAT and ::testing::AnyOf
…ators This builds on the work done by qndel in diasurgical#2084. I have not updated any of the call sites identified in that PR as I wanted to make it obvious that this does not change existing code. This is more of a discussion point at the moment. I was thinking that namespaces would be a good way to delineate behaviour. I've implemented "vanilla" to cover the base game logic and bugs. "randomV1" is based on diasurgical#2084 and uses STL concepts to add convenience functions as discussed in diasurgical#2193. The API design is intended to be common between versions. The next step would be to update the vanilla namespace functions to align with member functions of vanilla::RandomEngine. The reason for having this class is to allow creating a RandomEngine object and passing it in to the level/item generation code (for example) to make it clearer how a given object/dungeon layout is generated. Looking at code such as quests.cpp:165 makes me think a "vanillaSafe" namespace which fixes the negative number bug would be useful, but this would be a future enhancement iff this proposal is acceptable. Add libgmock-dev to the install script for linux_x86_64_test to use EXPECT_THAT and ::testing::AnyOf
Replaces crappy vanilla rng with a decent one for everything that doesn't break save compatibility (At least I hope so :D)