MADNESS  0.10.1
ran.h
Go to the documentation of this file.
1 /*
2  This file is part of MADNESS.
3 
4  Copyright (C) 2007,2010 Oak Ridge National Laboratory
5 
6  This program is free software; you can redistribute it and/or modify
7  it under the terms of the GNU General Public License as published by
8  the Free Software Foundation; either version 2 of the License, or
9  (at your option) any later version.
10 
11  This program is distributed in the hope that it will be useful,
12  but WITHOUT ANY WARRANTY; without even the implied warranty of
13  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14  GNU General Public License for more details.
15 
16  You should have received a copy of the GNU General Public License
17  along with this program; if not, write to the Free Software
18  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 
20  For more information please contact:
21 
22  Robert J. Harrison
23  Oak Ridge National Laboratory
24  One Bethel Valley Road
25  P.O. Box 2008, MS-6367
26 
27  email: harrisonrj@ornl.gov
28  tel: 865-241-3937
29  fax: 865-572-0680
30 */
31 
32 #ifndef MADNESS_MISC_RAN_H__INCLUDED
33 #define MADNESS_MISC_RAN_H__INCLUDED
34 
35 #include <madness/madness_config.h>
36 #include <madness/world/thread.h>
37 
38 #include <complex>
39 typedef std::complex<float> float_complex;
40 typedef std::complex<double> double_complex;
41 
42 
43 namespace madness {
44 
45  struct RandomState {
46  int cur;
47  double u[1279];
48  };
49 
50  /// A random number generator (portable, vectorized, and thread-safe)
51 
52  /// Following Brent 1992, we use a 48-bit generalized Fibonacci generator
53  /// \code
54  /// u[n] = alpha*u[n-r] + beta*u[n-s] mod m
55  /// \endcode
56  /// with alpha=1, beta=7, r=1279, s=861, m=2^48. Double precision
57  /// numbers are used to perform exact integer arithmetic. 48-bit
58  /// because we have 52 bits of mantissa, alpha+1 is 3 bits and 1 bit spare.
59  ///
60  /// The period is nominally 2^m (2^r - 1) / 2 but if p is the period,
61  /// X[n] and X[n+p/2k] differ by at most k bits (0 < k < 48) so usage
62  /// should be limited to the first 2^r-1 entries (about 10^385 values).
63  ///
64  /// Each instance provides a separate stream, but it is up to the
65  /// user to partition the sequence by selecting distinct seeds or
66  /// other means.
67  ///
68  /// The streams are thread safe.
69  ///
70  /// A default stream is provided as madness::default_random_generator.
71  class Random : private Mutex {
72  private:
73  const int r;
74  const int s;
75  const double beta;
76  int cur; // Removed volatile since always access in scope of mutex with implied barriers
77  double* const u;
78  unsigned int simple_state;
79 
80  void generate();
81 
82  unsigned int simple();
83 
84  public:
85  Random(unsigned int seed = 5461);
86 
87  virtual ~Random();
88 
89  double get() {
90  ScopedMutex<Mutex> safe(this);
91  if (cur >= r) generate();
92  return u[cur++];
93  }
94 
95  /// Returns a vector of uniform doubles in [0,1)
96  template <typename T>
97  void getv(int n, T * MADNESS_RESTRICT v) {
98  ScopedMutex<Mutex> safe(this);
99  while (n) {
100  if (cur >= r) generate();
101  int ndo = std::min(n,r-cur);
102  const double* ucur = const_cast<const double*>(u) + cur;
103  for (int i=0; i<ndo; ++i) v[i] = (T)(ucur[i]);
104  n -= ndo;
105  v += ndo;
106  cur += ndo;
107  }
108  }
109 
110  /// Returns vector of random bytes in [0,256)
111  void getbytes(int n, unsigned char * MADNESS_RESTRICT v);
112 
113  /// Returns full state of the generator
114  RandomState getstate() const;
115 
116  /// Restores state of the generator
117  void setstate(const RandomState &s);
118 
119  /// Sets state of the generator from integer
120  void setstate(unsigned int seed);
121 
122  /// Test the generator
123  static void test();
124  };
125 
126 
127  /// The default random number stream
128  extern Random default_random_generator;
129 
130  /// Random value that wraps the default Fibonacci generator
131  template <class T> T RandomValue();
132 
133  /// Random double
134  template <> double RandomValue<double> ();
135 
136  /// Random float
137  template <> float RandomValue<float> ();
138 
139  /// Random int
140  template <> int RandomValue<int> ();
141 
142  /// Random long
143  template <> long RandomValue<long> ();
144 
145  /// Random double_complex
147 
148  /// Random float_complex
150 
151  template <class T> void RandomVector(int n, T* t) {
152  for (int i=0; i<n; ++i) t[i] = RandomValue<T>();
153  }
154 
155  template <> void RandomVector<double>(int n, double* t);
156 
157  template <> void RandomVector<float>(int n, float* t);
158 
159  template <> void RandomVector<double_complex>(int n, double_complex* t);
160 
161  template <> void RandomVector<float_complex>(int n, float_complex* t);
162 }
163 
164 #endif // MADNESS_MISC_RAN_H__INCLUDED
std::complex< double > double_complex
Definition: cfft.h:14
Mutex using pthread mutex operations.
Definition: worldmutex.h:131
A random number generator (portable, vectorized, and thread-safe)
Definition: ran.h:71
void getbytes(int n, unsigned char *MADNESS_RESTRICT v)
Returns vector of random bytes in [0,256)
Definition: ran.cc:154
const double beta
Definition: ran.h:75
unsigned int simple_state
Definition: ran.h:78
Random(unsigned int seed=5461)
Definition: ran.cc:71
double *const u
Definition: ran.h:77
const int s
Definition: ran.h:74
static void test()
Test the generator.
Definition: ran.cc:182
virtual ~Random()
Definition: ran.cc:127
void setstate(const RandomState &s)
Restores state of the generator.
Definition: ran.cc:175
void getv(int n, T *MADNESS_RESTRICT v)
Returns a vector of uniform doubles in [0,1)
Definition: ran.h:97
RandomState getstate() const
Returns full state of the generator.
Definition: ran.cc:167
unsigned int simple()
Definition: ran.cc:66
double get()
Definition: ran.h:89
const int r
Definition: ran.h:73
int cur
Definition: ran.h:76
void generate()
Definition: ran.cc:45
Mutex that is applied/released at start/end of a scope.
Definition: worldmutex.h:239
auto T(World &world, response_space &f) -> response_space
Definition: global_functions.cc:34
static const double v
Definition: hatom_sf_dirac.cc:20
Macros and tools pertaining to the configuration of MADNESS.
File holds all helper structures necessary for the CC_Operator and CC2 class.
Definition: DFParameters.h:10
void RandomVector(int n, T *t)
Definition: ran.h:151
float RandomValue< float >()
Random float.
Definition: ran.cc:238
double RandomValue< double >()
Random double.
Definition: ran.cc:234
void RandomVector< float >(int n, float *t)
Definition: ran.cc:262
long RandomValue< long >()
Random long.
Definition: ran.cc:254
int RandomValue< int >()
Random int.
Definition: ran.cc:250
float_complex RandomValue< float_complex >()
Random float_complex.
Definition: ran.cc:246
double_complex RandomValue< double_complex >()
Random double_complex.
Definition: ran.cc:242
void RandomVector< float_complex >(int n, float_complex *t)
Definition: ran.cc:270
T RandomValue()
Random value that wraps the default Fibonacci generator.
void RandomVector< double >(int n, double *t)
Definition: ran.cc:258
void RandomVector< double_complex >(int n, double_complex *t)
Definition: ran.cc:266
Random default_random_generator
The default random number stream.
Definition: ran.cc:231
std::complex< double > double_complex
Definition: ran.h:40
std::complex< float > float_complex
Definition: ran.h:39
Definition: ran.h:45
double u[1279]
Definition: ran.h:47
int cur
Definition: ran.h:46
Implements Dqueue, Thread, ThreadBase and ThreadPool.