diff options
author | Evgeny Grechnikov <diamondaz@yandex.ru> | 2022-02-10 16:46:20 +0300 |
---|---|---|
committer | Daniil Cherednik <dcherednik@yandex-team.ru> | 2022-02-10 16:46:20 +0300 |
commit | 6e38f52f898d7c077ddd319800b4014967a5ca76 (patch) | |
tree | f0b2473cfc98506158b8f1d3d387c4f478ade18e /util/random | |
parent | bd085aee9b4f7a0bee302ce687964ffb7098f986 (diff) | |
download | ydb-6e38f52f898d7c077ddd319800b4014967a5ca76.tar.gz |
Restoring authorship annotation for Evgeny Grechnikov <diamondaz@yandex.ru>. Commit 1 of 2.
Diffstat (limited to 'util/random')
-rw-r--r-- | util/random/fast.h | 8 | ||||
-rw-r--r-- | util/random/fast_ut.cpp | 44 | ||||
-rw-r--r-- | util/random/lcg_engine.cpp | 50 | ||||
-rw-r--r-- | util/random/lcg_engine.h | 26 |
4 files changed, 64 insertions, 64 deletions
diff --git a/util/random/fast.h b/util/random/fast.h index ddc5711641..f86b56c625 100644 --- a/util/random/fast.h +++ b/util/random/fast.h @@ -73,10 +73,10 @@ public: } inline void Advance(ui64 delta) noexcept { - R1_.Advance(delta); - R2_.Advance(delta); - } - + R1_.Advance(delta); + R2_.Advance(delta); + } + private: TFastRng32Base R1_; TFastRng32Base R2_; diff --git a/util/random/fast_ut.cpp b/util/random/fast_ut.cpp index 60994a98b0..a641a30071 100644 --- a/util/random/fast_ut.cpp +++ b/util/random/fast_ut.cpp @@ -42,34 +42,34 @@ Y_UNIT_TEST_SUITE(TTestFastRng) { UNIT_ASSERT_VALUES_EQUAL(rng.Uniform(100u), i); } } - + Y_UNIT_TEST(TestAdvance) { - TReallyFastRng32 rng1(17); - TReallyFastRng32 rng2(17); + TReallyFastRng32 rng1(17); + TReallyFastRng32 rng2(17); for (size_t i = 0; i < 100; i++) { - rng1.GenRand(); + rng1.GenRand(); } - rng2.Advance(100); - UNIT_ASSERT_VALUES_EQUAL(rng1.GenRand(), rng2.GenRand()); - - TFastRng64 rng3(0, 1, 2, 3); - TFastRng64 rng4(0, 1, 2, 3); + rng2.Advance(100); + UNIT_ASSERT_VALUES_EQUAL(rng1.GenRand(), rng2.GenRand()); + + TFastRng64 rng3(0, 1, 2, 3); + TFastRng64 rng4(0, 1, 2, 3); for (size_t i = 0; i < 100; i++) { - rng3.GenRand(); + rng3.GenRand(); } - rng4.Advance(100); - UNIT_ASSERT_VALUES_EQUAL(rng3.GenRand(), rng4.GenRand()); - } - + rng4.Advance(100); + UNIT_ASSERT_VALUES_EQUAL(rng3.GenRand(), rng4.GenRand()); + } + Y_UNIT_TEST(TestAdvanceBoundaries) { - TReallyFastRng32 rng1(17); - TReallyFastRng32 rng2(17); - TReallyFastRng32 rng3(17); - rng2.Advance(0); - rng3.Advance(1); - UNIT_ASSERT_VALUES_EQUAL(rng1.GenRand(), rng2.GenRand()); - UNIT_ASSERT_VALUES_EQUAL(rng1.GenRand(), rng3.GenRand()); - } + TReallyFastRng32 rng1(17); + TReallyFastRng32 rng2(17); + TReallyFastRng32 rng3(17); + rng2.Advance(0); + rng3.Advance(1); + UNIT_ASSERT_VALUES_EQUAL(rng1.GenRand(), rng2.GenRand()); + UNIT_ASSERT_VALUES_EQUAL(rng1.GenRand(), rng3.GenRand()); + } Y_UNIT_TEST(TestCopy) { TReallyFastRng32 r1(1); diff --git a/util/random/lcg_engine.cpp b/util/random/lcg_engine.cpp index e1469104fa..e875705bcf 100644 --- a/util/random/lcg_engine.cpp +++ b/util/random/lcg_engine.cpp @@ -1,30 +1,30 @@ #include "lcg_engine.h" - -namespace NPrivate { - template <typename T> + +namespace NPrivate { + template <typename T> T LcgAdvance(T seed, T lcgBase, T lcgAddend, T delta) noexcept { - // seed[n+1] = A * seed[n] + B, A = lcgBase, B = lcgAddend - // seed[n] = A**n * seed[0] + (A**n - 1) / (A - 1) * B - // (initial value of n) = m * 2**k + (lower bits of n) - T mask = 1; - while (mask != (1ULL << (8 * sizeof(T) - 1)) && (mask << 1) <= delta) { - mask <<= 1; - } - T apow = 1; // A**m - T adiv = 0; // (A**m-1)/(A-1) - for (; mask; mask >>= 1) { - // m *= 2 - adiv *= apow + 1; - apow *= apow; - if (delta & mask) { - // m++ - adiv += apow; - apow *= lcgBase; - } - } - return seed * apow + lcgAddend * adiv; - } - + // seed[n+1] = A * seed[n] + B, A = lcgBase, B = lcgAddend + // seed[n] = A**n * seed[0] + (A**n - 1) / (A - 1) * B + // (initial value of n) = m * 2**k + (lower bits of n) + T mask = 1; + while (mask != (1ULL << (8 * sizeof(T) - 1)) && (mask << 1) <= delta) { + mask <<= 1; + } + T apow = 1; // A**m + T adiv = 0; // (A**m-1)/(A-1) + for (; mask; mask >>= 1) { + // m *= 2 + adiv *= apow + 1; + apow *= apow; + if (delta & mask) { + // m++ + adiv += apow; + apow *= lcgBase; + } + } + return seed * apow + lcgAddend * adiv; + } + template ui32 LcgAdvance<ui32>(ui32, ui32, ui32, ui32) noexcept; template ui64 LcgAdvance<ui64>(ui64, ui64, ui64, ui64) noexcept; } diff --git a/util/random/lcg_engine.h b/util/random/lcg_engine.h index 08cc93c845..0de277cb66 100644 --- a/util/random/lcg_engine.h +++ b/util/random/lcg_engine.h @@ -6,11 +6,11 @@ // common engine for lcg-based RNG's // http://en.wikipedia.org/wiki/Linear_congruential_generator -namespace NPrivate { - template <typename T> +namespace NPrivate { + template <typename T> T LcgAdvance(T seed, T lcgBase, T lcgAddend, T delta) noexcept; -}; - +}; + template <typename T, T A, T C> struct TFastLcgIterator { static_assert(C % 2 == 1, "C must be odd"); @@ -18,10 +18,10 @@ struct TFastLcgIterator { static constexpr T Iterate(T x) noexcept { return x * A + C; } - + static inline T IterateMultiple(T x, T delta) noexcept { - return ::NPrivate::LcgAdvance(x, A, C, delta); - } + return ::NPrivate::LcgAdvance(x, A, C, delta); + } }; template <typename T, T A> @@ -36,9 +36,9 @@ struct TLcgIterator { } inline T IterateMultiple(T x, T delta) noexcept { - return ::NPrivate::LcgAdvance(x, A, C, delta); - } - + return ::NPrivate::LcgAdvance(x, A, C, delta); + } + const T C; }; @@ -59,8 +59,8 @@ struct TLcgRngBase: public TIterator, public TMixer { } inline void Advance(TStateType delta) noexcept { - X = this->IterateMultiple(X, delta); - } - + X = this->IterateMultiple(X, delta); + } + TStateType X; }; |