33 #ifndef __r123_uniform_dot_hpp 34 #define __r123_uniform_dot_hpp 88 #include <Random123/features/compilerfeatures.h> 92 #if RANDOM_ITERATOR_R123_USE_CXX11_TYPE_TRAITS 93 #include <type_traits> 95 #if __cplusplus >= 201103L 105 #if RANDOM_ITERATOR_R123_USE_CXX11_TYPE_TRAITS 106 using std::make_signed;
107 using std::make_unsigned;
112 template <
typename T>
113 struct make_signed {};
114 template <
typename T>
115 struct make_unsigned {};
116 #define RANDOM_ITERATOR_R123_MK_SIGNED_UNSIGNED(ST, UT) \ 118 struct make_signed<ST> { \ 122 struct make_signed<UT> { \ 126 struct make_unsigned<ST> { \ 130 struct make_unsigned<UT> { \ 134 RANDOM_ITERATOR_R123_MK_SIGNED_UNSIGNED(int8_t, uint8_t);
135 RANDOM_ITERATOR_R123_MK_SIGNED_UNSIGNED(int16_t, uint16_t);
136 RANDOM_ITERATOR_R123_MK_SIGNED_UNSIGNED(int32_t, uint32_t);
137 RANDOM_ITERATOR_R123_MK_SIGNED_UNSIGNED(int64_t, uint64_t);
138 #if RANDOM_ITERATOR_R123_USE_GNU_UINT128 139 RANDOM_ITERATOR_R123_MK_SIGNED_UNSIGNED(__int128_t, __uint128_t);
141 #undef RANDOM_ITERATOR_R123_MK_SIGNED_UNSIGNED 144 #if defined(__CUDACC__) || defined(_LIBCPP_HAS_NO_CONSTEXPR) 156 template <
typename T>
157 RANDOM_ITERATOR_R123_CONSTEXPR RANDOM_ITERATOR_R123_STATIC_INLINE
158 RANDOM_ITERATOR_R123_CUDA_DEVICE T
160 typedef typename make_unsigned<T>::type uT;
161 return (~uT(0)) >> std::numeric_limits<T>::is_signed;
164 template <
typename T>
165 RANDOM_ITERATOR_R123_CONSTEXPR RANDOM_ITERATOR_R123_STATIC_INLINE T maxTvalue() {
166 return std::numeric_limits<T>::max();
192 template <
typename Ftype,
typename Itype>
193 RANDOM_ITERATOR_R123_CUDA_DEVICE RANDOM_ITERATOR_R123_STATIC_INLINE Ftype
195 typedef typename make_unsigned<Itype>::type Utype;
196 RANDOM_ITERATOR_R123_CONSTEXPR Ftype factor =
197 Ftype(1.) / (maxTvalue<Utype>() + Ftype(1.));
198 RANDOM_ITERATOR_R123_CONSTEXPR Ftype halffactor = Ftype(0.5) * factor;
199 #if RANDOM_ITERATOR_R123_UNIFORM_FLOAT_STORE 200 volatile Ftype x = Utype(in) * factor;
201 return x + halffactor;
203 return Utype(in) * factor + halffactor;
226 template <
typename Ftype,
typename Itype>
227 RANDOM_ITERATOR_R123_CUDA_DEVICE RANDOM_ITERATOR_R123_STATIC_INLINE Ftype
229 typedef typename make_signed<Itype>::type Stype;
230 RANDOM_ITERATOR_R123_CONSTEXPR Ftype factor =
231 Ftype(1.) / (maxTvalue<Stype>() + Ftype(1.));
232 RANDOM_ITERATOR_R123_CONSTEXPR Ftype halffactor = Ftype(0.5) * factor;
233 #if RANDOM_ITERATOR_R123_UNIFORM_FLOAT_STORE 234 volatile Ftype x = Stype(in) * factor;
235 return x + halffactor;
237 return Stype(in) * factor + halffactor;
262 template <
typename Ftype,
typename Itype>
263 RANDOM_ITERATOR_R123_CUDA_DEVICE RANDOM_ITERATOR_R123_STATIC_INLINE Ftype
265 typedef typename make_unsigned<Itype>::type Utype;
266 RANDOM_ITERATOR_R123_CONSTEXPR
int excess =
267 std::numeric_limits<Utype>::digits - std::numeric_limits<Ftype>::digits;
269 RANDOM_ITERATOR_R123_CONSTEXPR
int ex_nowarn = (excess >= 0) ? excess : 0;
270 RANDOM_ITERATOR_R123_CONSTEXPR Ftype factor =
271 Ftype(1.) / (Ftype(1.) + ((maxTvalue<Utype>() >> ex_nowarn)));
272 return (1 | (Utype(in) >> ex_nowarn)) * factor;
274 return u01<Ftype>(in);
277 #if RANDOM_ITERATOR_R123_USE_CXX11_STD_ARRAY 285 template <
typename Ftype,
typename CollType>
286 static inline std::array<Ftype, CollType::static_size> u01all(CollType in) {
287 std::array<Ftype, CollType::static_size> ret;
289 for (
auto e : in) { ret[i++] = u01<Ftype>(e); }
299 template <
typename Ftype,
typename CollType>
300 static inline std::array<Ftype, CollType::static_size> uneg11all(CollType in) {
301 std::array<Ftype, CollType::static_size> ret;
303 for (
auto e : in) { ret[i++] = uneg11<Ftype>(e); }
313 template <
typename Ftype,
typename CollType>
314 static inline std::array<Ftype, CollType::static_size> u01fixedptall(CollType in) {
315 std::array<Ftype, CollType::static_size> ret;
317 for (
auto e : in) { ret[i++] = u01fixedpt<Ftype>(e); }
320 #endif // __cplusplus >= 201103L