C++ mpi module for stochmagnet_main Package
uniform01_dist.hpp
1 // Copyright (c) 2000-2022, Heiko Bauke
2 // All rights reserved.
3 //
4 // Redistribution and use in source and binary forms, with or without
5 // modification, are permitted provided that the following conditions
6 // are met:
7 //
8 // * Redistributions of source code must retain the above copyright
9 // notice, this list of conditions and the following disclaimer.
10 //
11 // * Redistributions in binary form must reproduce the above
12 // copyright notice, this list of conditions and the following
13 // disclaimer in the documentation and/or other materials provided
14 // with the distribution.
15 //
16 // * Neither the name of the copyright holder nor the names of its
17 // contributors may be used to endorse or promote products derived
18 // from this software without specific prior written permission.
19 //
20 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
21 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
23 // FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
24 // COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
25 // INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
26 // (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
27 // SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
28 // HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
29 // STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
30 // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
31 // OF THE POSSIBILITY OF SUCH DAMAGE.
32 
33 #if !(defined TRNG_UNIFORM01_DIST_HPP)
34 
35 #define TRNG_UNIFORM01_DIST_HPP
36 
37 #include <trng/cuda.hpp>
38 #include <trng/limits.hpp>
39 #include <trng/utility.hpp>
40 #include <ostream>
41 #include <istream>
42 #include <cerrno>
43 #include <ciso646>
44 
45 namespace trng {
46 
47  // uniform random number generator class
48  template<typename float_t = double>
50  public:
51  using result_type = float_t;
52 
53  class param_type {
54  public:
55  param_type() = default;
56 
57  friend class uniform01_dist<float_t>;
58 
59  // Equality comparable concept
60  friend TRNG_CUDA_ENABLE inline bool operator==(const param_type &, const param_type &) {
61  return true;
62  }
63 
64  friend TRNG_CUDA_ENABLE inline bool operator!=(const param_type &, const param_type &) {
65  return false;
66  }
67 
68  // Streamable concept
69  template<typename char_t, typename traits_t>
70  friend std::basic_ostream<char_t, traits_t> &operator<<(
71  std::basic_ostream<char_t, traits_t> &out, const param_type &) {
72  std::ios_base::fmtflags flags(out.flags());
73  out.flags(std::ios_base::dec | std::ios_base::fixed | std::ios_base::left);
74  out << '(' << ')';
75  out.flags(flags);
76  return out;
77  }
78 
79  template<typename char_t, typename traits_t>
80  friend std::basic_istream<char_t, traits_t> &operator>>(
81  std::basic_istream<char_t, traits_t> &in, param_type &) {
82  std::ios_base::fmtflags flags(in.flags());
83  in.flags(std::ios_base::dec | std::ios_base::fixed | std::ios_base::left);
84  in >> utility::delim('(') >> utility::delim(')');
85  in.flags(flags);
86  return in;
87  }
88  };
89 
90  private:
91  param_type p;
92 
93  public:
94  // constructor
95  uniform01_dist() = default;
96  TRNG_CUDA_ENABLE
97  explicit uniform01_dist(const param_type &) {}
98  // reset internal state
99  TRNG_CUDA_ENABLE
100  void reset() {}
101  // random numbers
102  template<typename R>
103  TRNG_CUDA_ENABLE result_type operator()(R &r) {
104  return utility::uniformco<result_type>(r);
105  }
106  template<typename R>
107  TRNG_CUDA_ENABLE result_type operator()(R &r, const param_type &) {
108  return utility::uniformco<result_type>(r);
109  }
110  // property methods
111  // min / max
112  TRNG_CUDA_ENABLE
113  result_type min() const { return 0; }
114  TRNG_CUDA_ENABLE
115  result_type max() const { return 1; }
116  TRNG_CUDA_ENABLE
117  param_type param() const { return p; }
118  TRNG_CUDA_ENABLE
119  void param(const param_type &) {}
120  // probability density function
121  TRNG_CUDA_ENABLE
122  result_type pdf(result_type x) const {
123  if (x < 0 or x >= 1)
124  return 0;
125  return 1;
126  }
127  // cumulative density function
128  TRNG_CUDA_ENABLE
129  result_type cdf(result_type x) const {
130  if (x < 0)
131  return 0;
132  if (x >= 1)
133  return 1;
134  return x;
135  }
136  // inverse cumulative density function
137  TRNG_CUDA_ENABLE
138  result_type icdf(result_type x) const {
139  if (x < 0 or x > 1) {
140 #if !(defined TRNG_CUDA)
141  errno = EDOM;
142 #endif
143  return math::numeric_limits<result_type>::quiet_NaN();
144  }
145  return x;
146  }
147  };
148 
149  // -------------------------------------------------------------------
150 
151  // Equality comparable concept
152  template<typename float_t>
153  TRNG_CUDA_ENABLE inline bool operator==(const uniform01_dist<float_t> &g1,
154  const uniform01_dist<float_t> &g2) {
155  return g1.param() == g2.param();
156  }
157 
158  template<typename float_t>
159  TRNG_CUDA_ENABLE inline bool operator!=(const uniform01_dist<float_t> &g1,
160  const uniform01_dist<float_t> &g2) {
161  return g1.param() != g2.param();
162  }
163 
164  // Streamable concept
165  template<typename char_t, typename traits_t, typename float_t>
166  std::basic_ostream<char_t, traits_t> &operator<<(std::basic_ostream<char_t, traits_t> &out,
167  const uniform01_dist<float_t> &g) {
168  std::ios_base::fmtflags flags(out.flags());
169  out.flags(std::ios_base::dec | std::ios_base::fixed | std::ios_base::left);
170  out << "[uniform01 " << g.param() << ']';
171  out.flags(flags);
172  return out;
173  }
174 
175  template<typename char_t, typename traits_t, typename float_t>
176  std::basic_istream<char_t, traits_t> &operator>>(std::basic_istream<char_t, traits_t> &in,
177  uniform01_dist<float_t> &g) {
178  typename uniform01_dist<float_t>::param_type P;
179  std::ios_base::fmtflags flags(in.flags());
180  in.flags(std::ios_base::dec | std::ios_base::fixed | std::ios_base::left);
181  in >> utility::ignore_spaces() >> utility::delim("[uniform01 ") >> P >> utility::delim(']');
182  if (in)
183  g.param(P);
184  in.flags(flags);
185  return in;
186  }
187 
188 } // namespace trng
189 
190 #endif
Definition: uniform01_dist.hpp:53
Definition: uniform01_dist.hpp:49