blob: a8d88f6f77e3db8a6655e919beb0c210c67b7c00 (
plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
|
#ifndef eyNJdhz0jqVQc4zddlEi67woThg
#define eyNJdhz0jqVQc4zddlEi67woThg
// TODO: use proper PRNG
#include <stdlib.h>
#include <inttypes.h>
#include <math.h>
#include <boost/random.hpp>
#include <boost/random/uniform_int.hpp>
#include <boost/random/exponential_distribution.hpp>
#include <boost/random/variate_generator.hpp>
#include <boost/static_assert.hpp>
#include "template_helpers.hpp"
#include <boost/random/ranlux.hpp>
#include <boost/random/additive_combine.hpp>
namespace RNG {
typedef boost::ecuyer1988 generator;
struct seed_t {
generator rng;
seed_t() : rng(0) {}
template<typename T>
explicit seed_t(T x) : rng(x + 17 * x + 257 * x) {}
seed_t & operator= (seed_t x) {
rng = x.rng;
return *this;
}
template<typename T>
seed_t & operator= (T x) {
rng.seed(x);
return *this;
}
};
seed_t next(seed_t last, int amount=1) {
boost::uniform_int<uint64_t> dist;
for (int i=0; i<amount; i++)
dist(last.rng);
return last;
}
seed_t split(seed_t old) {
boost::uniform_int<uint64_t> dist(0, -1);
uint64_t s = 0;
for (int i=0; i<37; i++) {
s ^= dist(old.rng);
s ^= ~(s << 1);
}
// std::cout << "new seed: " << s << std::endl;
return seed_t(s);
}
uint32_t integer(seed_t s, uint32_t num) {
boost::uniform_int<uint32_t> gen(0, num-1);
return gen(s.rng);
}
// returns val \in [0,1)
double equi(seed_t s) {
boost::uniform_01<double> dist;
return dist(s.rng);
}
double expo(seed_t s, double mean) {
typedef boost::exponential_distribution<double> dist;
boost::variate_generator<generator &, dist> gen(s.rng, dist(1.0 / mean));
double res = gen();
return res;
}
}
namespace std {
std::ostream& operator<< (std::ostream &os, RNG::seed_t s) {
return os << "rand48(" << s.rng << ")";
}
}
#endif // eyNJdhz0jqVQc4zddlEi67woThg
|