Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #pragma once
- #include"base/dependencies/index.hpp"
- #include"debug.hpp"
- #include"floats.hpp"
- #include"integers.hpp"
- #include"metaprogramming.hpp"
- // Return a random unsigned 64-bit seed.
- u64 random_seed(){
- // Read a hardware-generated random unsigned 64-bit value.
- u64 seed=0;
- _rdrand64_step(&seed);
- // Add noise using a standard uniform random number generator.
- static random_device rd;
- seed^=(U64(rd())<<32)|rd();
- // Add noise using the current time.
- seed^=chrono::steady_clock::now().time_since_epoch().count();
- // Add noise using a random address from the heap.
- seed^=reinterpret_cast<u64>(make_unique<char>().get());
- // Return the final value.
- return seed;
- }
- // Default random engine.
- using random_engine=CXX::sfmt19937_64;
- // Generic random utility type.
- template<class RandomEngine=random_engine>class random_machine{
- // Seed unsigned integer type.
- using seed_type=RandomEngine::result_type;
- // Initialized random number engine.
- static inline RandomEngine engine{static_cast<seed_type>(random_seed())};
- public:
- // Generate a random integer in `[l,r)`.
- template<Integer Int>static Int integer(Int const l,Int const r){
- ASSERT(l<r);
- return uniform_int_distribution{l,r-1}(engine);
- }
- // Generate a random integer in `[0,n)`.
- template<Integer Int>static Int integer(Int const n){
- ASSERT(n>0);
- return integer<Int>(0,n);
- }
- // Generate a random real in `[0,1)`.
- template<Float Real=f64>
- static Real real(){return uniform_real_distribution<Real>{}(engine);}
- // Mix up the given container range randomly.
- template<class RandomIt>
- static void mixup(RandomIt first,RandomIt last){shuffle(first,last,engine);}
- };
- // Default random utility type.
- template class random_machine<>;
- using rnd=random_machine<>;
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement