GNU Octave  8.1.0
A high-level interpreted language, primarily intended for numerical computations, mostly compatible with Matlab
randmtzig.cc
Go to the documentation of this file.
1 ////////////////////////////////////////////////////////////////////////
2 //
3 // Copyright (C) 2006-2023 The Octave Project Developers
4 //
5 // See the file COPYRIGHT.md in the top-level directory of this
6 // distribution or <https://octave.org/copyright/>.
7 //
8 // This file is part of Octave.
9 //
10 // Octave is free software: you can redistribute it and/or modify it
11 // under the terms of the GNU General Public License as published by
12 // the Free Software Foundation, either version 3 of the License, or
13 // (at your option) any later version.
14 //
15 // Octave is distributed in the hope that it will be useful, but
16 // WITHOUT ANY WARRANTY; without even the implied warranty of
17 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 // GNU General Public License for more details.
19 //
20 // You should have received a copy of the GNU General Public License
21 // along with Octave; see the file COPYING. If not, see
22 // <https://www.gnu.org/licenses/>.
23 //
24 ////////////////////////////////////////////////////////////////////////
25 
26 /*
27  A C-program for MT19937, with initialization improved 2002/2/10.
28  Coded by Takuji Nishimura and Makoto Matsumoto.
29  This is a faster version by taking Shawn Cokus's optimization,
30  Matthe Bellew's simplification, Isaku Wada's real version.
31  David Bateman added normal and exponential distributions following
32  Marsaglia and Tang's Ziggurat algorithm.
33 
34  Copyright (C) 1997 - 2002, Makoto Matsumoto and Takuji Nishimura,
35  Copyright (C) 2004, David Bateman
36  All rights reserved.
37 
38  Redistribution and use in source and binary forms, with or without
39  modification, are permitted provided that the following conditions
40  are met:
41 
42  1. Redistributions of source code must retain the above copyright
43  notice, this list of conditions and the following disclaimer.
44 
45  2. Redistributions in binary form must reproduce the above copyright
46  notice, this list of conditions and the following disclaimer in the
47  documentation and/or other materials provided with the distribution.
48 
49  3. The names of its contributors may not be used to endorse or promote
50  products derived from this software without specific prior written
51  permission.
52 
53  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
54  "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
55  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
56  A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
57  OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
58  EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
59  PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
60  PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
61  LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
62  NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
63  SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
64 
65 
66  Any feedback is very welcome.
67  http://www.math.keio.ac.jp/matumoto/emt.html
68  email: matumoto@math.keio.ac.jp
69 
70  * 2004-01-19 Paul Kienzle
71  * * comment out main
72  * add init_by_entropy, get_state, set_state
73  * * converted to allow compiling by C++ compiler
74  *
75  * 2004-01-25 David Bateman
76  * * Add Marsaglia and Tsang Ziggurat code
77  *
78  * 2004-07-13 Paul Kienzle
79  * * make into an independent library with some docs.
80  * * introduce new main and test code.
81  *
82  * 2004-07-28 Paul Kienzle & David Bateman
83  * * add -DALLBITS flag for 32 vs. 53 bits of randomness in mantissa
84  * * make the naming scheme more uniform
85  * * add -DHAVE_X86 for faster support of 53 bit mantissa on x86 arch.
86  *
87  * 2005-02-23 Paul Kienzle
88  * * fix -DHAVE_X86_32 flag and add -DUSE_X86_32=0|1 for explicit control
89  *
90  * 2006-04-01 David Bateman
91  * * convert for use in octave, declaring static functions only used
92  * here and adding oct_ to functions visible externally
93  * * inverse sense of ALLBITS
94  *
95  * 2012-05-18 David Bateman
96  * * Remove randu64 and ALLBIT option
97  * * Add the single precision generators
98  */
99 
100 /*
101  === Build instructions ===
102 
103  Compile with -DHAVE_GETTIMEOFDAY if the gettimeofday function is
104  available. This is not necessary if your architecture has
105  /dev/urandom defined.
106 
107  Uses implicit -Di386 or explicit -DHAVE_X86_32 to determine if CPU=x86.
108  You can force X86 behavior with -DUSE_X86_32=1, or suppress it with
109  -DUSE_X86_32=0. You should also consider -march=i686 or similar for
110  extra performance. Check whether -DUSE_X86_32=0 is faster on 64-bit
111  x86 architectures.
112 
113  If you want to replace the Mersenne Twister with another
114  generator then redefine randi32 appropriately.
115 
116  === Usage instructions ===
117  Before using any of the generators, initialize the state with one of
118  the init_mersenne_twister functions.
119 
120  All generators share the same state vector.
121 
122  === Mersenne Twister ===
123  random initial state:
124  void init_mersenne_twister (void)
125 
126  // 32-bit initial state:
127  void init_mersenne_twister (uint32_t s)
128 
129  // m*32-bit initial state:
130  void init_mersenne_twister (uint32_t k[],int m)
131 
132  // saves state in array:
133  void get_mersenne_twister_state (uint32_t save[MT_N+1])
134 
135  // restores state from array
136  void set_mersenne_twister_state (uint32_t save[MT_N+1])
137 
138  static uint32_t randmt (void) returns 32-bit unsigned int
139 
140  === inline generators ===
141  static uint32_t randi32 (void) returns 32-bit unsigned int
142  static uint64_t randi53 (void) returns 53-bit unsigned int
143  static uint64_t randi54 (void) returns 54-bit unsigned int
144  static float randu24 (void) returns 24-bit uniform in (0,1)
145  static double randu53 (void) returns 53-bit uniform in (0,1)
146 
147  double rand_uniform (void) returns M-bit uniform in (0,1)
148  double rand_normal (void) returns M-bit standard normal
149  double rand_exponential (void) returns N-bit standard exponential
150 
151  === Array generators ===
152  void rand_uniform (octave_idx_type, double [])
153  void rand_normal (octave_idx_type, double [])
154  void rand_exponential (octave_idx_type, double [])
155 */
156 
157 #if defined (HAVE_CONFIG_H)
158 # include "config.h"
159 #endif
160 
161 #include <cmath>
162 #include <cstdio>
163 #include <ctime>
164 
165 #include <algorithm>
166 #include <random>
167 
168 #include "oct-syscalls.h"
169 #include "oct-time.h"
170 #include "randmtzig.h"
171 
172 /* FIXME: may want to suppress X86 if sizeof(long) > 4 */
173 #if ! defined (USE_X86_32)
174 # if defined (i386) || defined (HAVE_X86_32)
175 # define USE_X86_32 1
176 # else
177 # define USE_X86_32 0
178 # endif
179 #endif
180 
182 
183 /* ===== Mersenne Twister 32-bit generator ===== */
184 
185 #define MT_M 397
186 #define MATRIX_A 0x9908b0dfUL /* constant vector a */
187 #define UMASK 0x80000000UL /* most significant w-r bits */
188 #define LMASK 0x7fffffffUL /* least significant r bits */
189 #define MIXBITS(u,v) ( ((u) & UMASK) | ((v) & LMASK) )
190 #define TWIST(u,v) ((MIXBITS(u,v) >> 1) ^ ((v)&1UL ? MATRIX_A : 0UL))
191 
192 static uint32_t *next;
193 static uint32_t state[MT_N]; /* the array for the state vector */
194 static int left = 1;
195 static int initf = 0;
196 static int initt = 1;
197 static int inittf = 1;
198 
199 /* initializes state[MT_N] with a seed */
200 void init_mersenne_twister (const uint32_t s)
201 {
202  int j;
203  state[0] = s & 0xffffffffUL;
204  for (j = 1; j < MT_N; j++)
205  {
206  state[j] = (1812433253UL * (state[j-1] ^ (state[j-1] >> 30)) + j);
207  /* See Knuth TAOCP Vol2. 3rd Ed. P.106 for multiplier. */
208  /* In the previous versions, MSBs of the seed affect */
209  /* only MSBs of the array state[]. */
210  /* 2002/01/09 modified by Makoto Matsumoto */
211  state[j] &= 0xffffffffUL; /* for >32 bit machines */
212  }
213  left = 1;
214  initf = 1;
215 }
216 
217 /* initialize by an array with array-length */
218 /* init_key is the array for initializing keys */
219 /* key_length is its length */
220 void init_mersenne_twister (const uint32_t *init_key, const int key_length)
221 {
222  int i, j, k;
223  init_mersenne_twister (19650218UL);
224  i = 1;
225  j = 0;
226  k = (MT_N > key_length ? MT_N : key_length);
227  for (; k; k--)
228  {
229  state[i] = (state[i] ^ ((state[i-1] ^ (state[i-1] >> 30)) * 1664525UL))
230  + init_key[j] + j; /* non linear */
231  state[i] &= 0xffffffffUL; /* for WORDSIZE > 32 machines */
232  i++;
233  j++;
234  if (i >= MT_N)
235  {
236  state[0] = state[MT_N-1];
237  i = 1;
238  }
239  if (j >= key_length)
240  j = 0;
241  }
242  for (k = MT_N - 1; k; k--)
243  {
244  state[i] = (state[i] ^ ((state[i-1] ^ (state[i-1] >> 30)) * 1566083941UL))
245  - i; /* non linear */
246  state[i] &= 0xffffffffUL; /* for WORDSIZE > 32 machines */
247  i++;
248  if (i >= MT_N)
249  {
250  state[0] = state[MT_N-1];
251  i = 1;
252  }
253  }
254 
255  state[0] = 0x80000000UL; /* MSB is 1; assuring nonzero initial array */
256  left = 1;
257  initf = 1;
258 }
259 
261 {
262  uint32_t entropy[MT_N];
263  int n = 0;
264 
265  // Gather some entropy from various sources
266 
267  sys::time now;
268 
269  // Current time in seconds
270  if (n < MT_N)
271  entropy[n++] = now.unix_time ();
272 
273  // CPU time used (usec)
274  if (n < MT_N)
275  entropy[n++] = clock ();
276 
277  // Fractional part of current time
278  if (n < MT_N)
279  entropy[n++] = now.usec ();
280 
281  // Include the PID to make sure that several processes reaching here at the
282  // same time use different random numbers.
283  if (n < MT_N)
284  entropy[n++] = sys::getpid ();
285 
286  if (n < MT_N)
287  {
288  try
289  {
290  // The standard doesn't *guarantee* that random_device provides
291  // non-deterministic random numbers. So add entropy from this
292  // source last to make sure we gathered at least some entropy from
293  // the earlier sources.
294  std::random_device rd;
295  std::uniform_int_distribution<uint32_t> dist;
296  // Add 1024 bit of "true" entropy
297  int n_max = std::min (n + 32, MT_N);
298  while (n < n_max)
299  entropy[n++] = dist (rd);
300  }
301  catch (const std::exception&)
302  {
303  // Just ignore any exception and skip that source of entropy.
304  }
305  }
306 
307  // Send all the entropy into the initial state vector
308  init_mersenne_twister (entropy, n);
309 }
310 
311 void set_mersenne_twister_state (const uint32_t *save)
312 {
313  std::copy_n (save, MT_N, state);
314  left = save[MT_N];
315  next = state + (MT_N - left + 1);
316 }
317 
318 void get_mersenne_twister_state (uint32_t *save)
319 {
320  std::copy_n (state, MT_N, save);
321  save[MT_N] = left;
322 }
323 
324 static void next_state (void)
325 {
326  uint32_t *p = state;
327  int j;
328 
329  /* if init_by_int() has not been called, */
330  /* a default initial seed is used */
331  /* if (initf==0) init_by_int(5489UL); */
332  /* Or better yet, a random seed! */
333  if (initf == 0)
335 
336  left = MT_N;
337  next = state;
338 
339  for (j = MT_N - MT_M + 1; --j; p++)
340  *p = p[MT_M] ^ TWIST(p[0], p[1]);
341 
342  for (j = MT_M; --j; p++)
343  *p = p[MT_M-MT_N] ^ TWIST(p[0], p[1]);
344 
345  *p = p[MT_M-MT_N] ^ TWIST(p[0], state[0]);
346 }
347 
348 /* generates a random number on [0,0xffffffff]-interval */
349 static uint32_t randmt (void)
350 {
351  uint32_t y;
352 
353  if (--left == 0)
354  next_state ();
355  y = *next++;
356 
357  /* Tempering */
358  y ^= (y >> 11);
359  y ^= (y << 7) & 0x9d2c5680UL;
360  y ^= (y << 15) & 0xefc60000UL;
361  return (y ^ (y >> 18));
362 }
363 
364 /* ===== Uniform generators ===== */
365 
366 /* Select which 32 bit generator to use */
367 #define randi32 randmt
368 
369 static uint64_t randi53 (void)
370 {
371  const uint32_t lo = randi32 ();
372  const uint32_t hi = randi32 () & 0x1FFFFF;
373 #if defined (HAVE_X86_32)
374  uint64_t u;
375  uint32_t *p = (uint32_t *)&u;
376  p[0] = lo;
377  p[1] = hi;
378  return u;
379 #else
380  return ((static_cast<uint64_t> (hi) << 32) | lo);
381 #endif
382 }
383 
384 static uint64_t randi54 (void)
385 {
386  const uint32_t lo = randi32 ();
387  const uint32_t hi = randi32 () & 0x3FFFFF;
388 #if defined (HAVE_X86_32)
389  uint64_t u;
390  uint32_t *p = static_cast<uint32_t *> (&u);
391  p[0] = lo;
392  p[1] = hi;
393  return u;
394 #else
395  return ((static_cast<uint64_t> (hi) << 32) | lo);
396 #endif
397 }
398 
399 /* generates a random number on (0,1)-real-interval */
400 static float randu24 (void)
401 {
402  uint32_t i;
403 
404  do
405  {
406  i = randi32 () & static_cast<uint32_t> (0xFFFFFF);
407  }
408  while (i == 0);
409 
410  return i * (1.0f / 16777216.0f);
411 }
412 
413 /* generates a random number on (0,1) with 53-bit resolution */
414 static double randu53 (void)
415 {
416  int32_t a, b;
417 
418  do
419  {
420  a = randi32 () >> 5;
421  b = randi32 () >> 6;
422  }
423  while (a == 0 && b == 0);
424 
425  return (a*67108864.0 + b) * (1.0/9007199254740992.0);
426 }
427 
428 /* Determine mantissa for uniform doubles */
429 template <>
432 {
433  return randu53 ();
434 }
435 
436 /* Determine mantissa for uniform floats */
437 template <>
439 rand_uniform<float> (void)
440 {
441  return randu24 ();
442 }
443 
444 /* ===== Ziggurat normal and exponential generators ===== */
445 
446 #define ZIGGURAT_TABLE_SIZE 256
447 
448 #define ZIGGURAT_NOR_R 3.6541528853610088
449 #define ZIGGURAT_NOR_INV_R 0.27366123732975828
450 #define NOR_SECTION_AREA 0.00492867323399
451 
452 #define ZIGGURAT_EXP_R 7.69711747013104972
453 #define ZIGGURAT_EXP_INV_R 0.129918765548341586
454 #define EXP_SECTION_AREA 0.0039496598225815571993
455 
456 #define ZIGINT uint64_t
457 #define EMANTISSA 9007199254740992.0 /* 53 bit mantissa */
458 #define ERANDI randi53() /* 53 bits for mantissa */
459 #define NMANTISSA EMANTISSA
460 #define NRANDI randi54() /* 53 bits for mantissa + 1 bit sign */
461 #define RANDU randu53()
462 
467 
468 /*
469  This code is based on the paper Marsaglia and Tsang, "The ziggurat method
470  for generating random variables", Journ. Statistical Software. Code was
471  presented in this paper for a Ziggurat of 127 levels and using a 32 bit
472  integer random number generator. This version of the code, uses the
473  Mersenne Twister as the integer generator and uses 256 levels in the
474  Ziggurat. This has several advantages.
475 
476  1) As Marsaglia and Tsang themselves states, the more levels the few
477  times the expensive tail algorithm must be called
478  2) The cycle time of the generator is determined by the integer
479  generator, thus the use of a Mersenne Twister for the core random
480  generator makes this cycle extremely long.
481  3) The license on the original code was unclear, thus rewriting the code
482  from the article means we are free of copyright issues.
483  4) Compile flag for full 53-bit random mantissa.
484 
485  It should be stated that the authors made my life easier, by the fact that
486  the algorithm developed in the text of the article is for a 256 level
487  ziggurat, even if the code itself isn't...
488 
489  One modification to the algorithm developed in the article, is that it is
490  assumed that 0 <= x < Inf, and "unsigned long"s are used, thus resulting in
491  terms like 2^32 in the code. As the normal distribution is defined between
492  -Inf < x < Inf, we effectively only have 31 bit integers plus a sign. Thus
493  in Marsaglia and Tsang, terms like 2^32 become 2^31. We use NMANTISSA for
494  this term. The exponential distribution is one sided so we use the
495  full 32 bits. We use EMANTISSA for this term.
496 
497  It appears that I'm slightly slower than the code in the article, this
498  is partially due to a better generator of random integers than they
499  use. But might also be that the case of rapid return was optimized by
500  inlining the relevant code with a #define. As the basic Mersenne
501  Twister is only 25% faster than this code I suspect that the main
502  reason is just the use of the Mersenne Twister and not the inlining,
503  so I'm not going to try and optimize further.
504 */
505 
507 {
508  int i;
509  double x, x1;
510 
511  /* Ziggurat tables for the normal distribution */
512  x1 = ZIGGURAT_NOR_R;
513  wi[255] = x1 / NMANTISSA;
514  fi[255] = exp (-0.5 * x1 * x1);
515 
516  /* Index zero is special for tail strip, where Marsaglia and Tsang
517  * defines this as
518  * k_0 = 2^31 * r * f(r) / v, w_0 = 0.5^31 * v / f(r), f_0 = 1,
519  * where v is the area of each strip of the ziggurat.
520  */
521  ki[0] = static_cast<ZIGINT> (x1 * fi[255] / NOR_SECTION_AREA * NMANTISSA);
522  wi[0] = NOR_SECTION_AREA / fi[255] / NMANTISSA;
523  fi[0] = 1.;
524 
525  for (i = 254; i > 0; i--)
526  {
527  /* New x is given by x = f^{-1}(v/x_{i+1} + f(x_{i+1})), thus
528  * need inverse operator of y = exp(-0.5*x*x) -> x = sqrt(-2*ln(y))
529  */
530  x = std::sqrt (-2. * std::log (NOR_SECTION_AREA / x1 + fi[i+1]));
531  ki[i+1] = static_cast<ZIGINT> (x / x1 * NMANTISSA);
532  wi[i] = x / NMANTISSA;
533  fi[i] = exp (-0.5 * x * x);
534  x1 = x;
535  }
536 
537  ki[1] = 0;
538 
539  /* Zigurrat tables for the exponential distribution */
540  x1 = ZIGGURAT_EXP_R;
541  we[255] = x1 / EMANTISSA;
542  fe[255] = exp (-x1);
543 
544  /* Index zero is special for tail strip, where Marsaglia and Tsang
545  * defines this as
546  * k_0 = 2^32 * r * f(r) / v, w_0 = 0.5^32 * v / f(r), f_0 = 1,
547  * where v is the area of each strip of the ziggurat.
548  */
549  ke[0] = static_cast<ZIGINT> (x1 * fe[255] / EXP_SECTION_AREA * EMANTISSA);
550  we[0] = EXP_SECTION_AREA / fe[255] / EMANTISSA;
551  fe[0] = 1.;
552 
553  for (i = 254; i > 0; i--)
554  {
555  /* New x is given by x = f^{-1}(v/x_{i+1} + f(x_{i+1})), thus
556  * need inverse operator of y = exp(-x) -> x = -ln(y)
557  */
558  x = - std::log (EXP_SECTION_AREA / x1 + fe[i+1]);
559  ke[i+1] = static_cast<ZIGINT> (x / x1 * EMANTISSA);
560  we[i] = x / EMANTISSA;
561  fe[i] = exp (-x);
562  x1 = x;
563  }
564  ke[1] = 0;
565 
566  initt = 0;
567 }
568 
569 /*
570  * Here is the guts of the algorithm. As Marsaglia and Tsang state the
571  * algorithm in their paper
572  *
573  * 1) Calculate a random signed integer j and let i be the index
574  * provided by the rightmost 8-bits of j
575  * 2) Set x = j * w_i. If j < k_i return x
576  * 3) If i = 0, then return x from the tail
577  * 4) If [f(x_{i-1}) - f(x_i)] * U < f(x) - f(x_i), return x
578  * 5) goto step 1
579  *
580  * Where f is the functional form of the distribution, which for a normal
581  * distribution is exp(-0.5*x*x)
582  */
583 
584 
585 template <> OCTAVE_API double rand_normal<double> (void)
586 {
587  if (initt)
589 
590  while (1)
591  {
592  /* The following code is specialized for 32-bit mantissa.
593  * Compared to the arbitrary mantissa code, there is a performance
594  * gain for 32-bits: PPC: 2%, MIPS: 8%, x86: 40%
595  * There is a bigger performance gain compared to using a full
596  * 53-bit mantissa: PPC: 60%, MIPS: 65%, x86: 240%
597  * Of course, different compilers and operating systems may
598  * have something to do with this.
599  */
600 # if defined (HAVE_X86_32)
601  /* 53-bit mantissa, 1-bit sign, x86 32-bit architecture */
602  double x;
603  int si, idx;
604  uint32_t lo, hi;
605  int64_t rabs;
606  uint32_t *p = (uint32_t *)&rabs;
607  lo = randi32 ();
608  idx = lo & 0xFF;
609  hi = randi32 ();
610  si = hi & UMASK;
611  p[0] = lo;
612  p[1] = hi & 0x1FFFFF;
613  x = ( si ? -rabs : rabs ) * wi[idx];
614 # else
615  /* arbitrary mantissa (selected by NRANDI, with 1 bit for sign) */
616  const uint64_t r = NRANDI;
617  const int64_t rabs = r >> 1;
618  const int idx = static_cast<int> (rabs & 0xFF);
619  const double x = ( (r & 1) ? -rabs : rabs) * wi[idx];
620 # endif
621  if (rabs < static_cast<int64_t> (ki[idx]))
622  return x; /* 99.3% of the time we return here 1st try */
623  else if (idx == 0)
624  {
625  /* As stated in Marsaglia and Tsang
626  *
627  * For the normal tail, the method of Marsaglia[5] provides:
628  * generate x = -ln(U_1)/r, y = -ln(U_2), until y+y > x*x,
629  * then return r+x. Except that r+x is always in the positive
630  * tail!!!! Any thing random might be used to determine the
631  * sign, but as we already have r we might as well use it
632  *
633  * [PAK] but not the bottom 8 bits, since they are all 0 here!
634  */
635  double xx, yy;
636  do
637  {
638  xx = - ZIGGURAT_NOR_INV_R * std::log (RANDU);
639  yy = - std::log (RANDU);
640  }
641  while ( yy+yy <= xx*xx);
642  return ((rabs & 0x100) ? -ZIGGURAT_NOR_R-xx : ZIGGURAT_NOR_R+xx);
643  }
644  else if ((fi[idx-1] - fi[idx]) * RANDU + fi[idx] < exp (-0.5*x*x))
645  return x;
646  }
647 }
648 
649 template <> OCTAVE_API double rand_exponential<double> (void)
650 {
651  if (initt)
653 
654  while (1)
655  {
656  ZIGINT ri = ERANDI;
657  const int idx = static_cast<int> (ri & 0xFF);
658  const double x = ri * we[idx];
659  if (ri < ke[idx])
660  return x; /* 98.9% of the time we return here 1st try */
661  else if (idx == 0)
662  {
663  /* As stated in Marsaglia and Tsang
664  *
665  * For the exponential tail, the method of Marsaglia[5] provides:
666  * x = r - ln(U);
667  */
668  return ZIGGURAT_EXP_R - std::log (RANDU);
669  }
670  else if ((fe[idx-1] - fe[idx]) * RANDU + fe[idx] < exp (-x))
671  return x;
672  }
673 }
674 
675 template <> OCTAVE_API void rand_uniform<double> (octave_idx_type n, double *p)
676 {
677  std::generate_n (p, n, [](void) { return rand_uniform<double> (); });
678 }
679 
680 template <> OCTAVE_API void rand_normal (octave_idx_type n, double *p)
681 {
682  std::generate_n (p, n, [](void) { return rand_normal<double> (); });
683 }
684 
685 template <> OCTAVE_API void rand_exponential (octave_idx_type n, double *p)
686 {
687  std::generate_n (p, n, [](void) { return rand_exponential<double> (); });
688 }
689 
690 #undef ZIGINT
691 #undef EMANTISSA
692 #undef ERANDI
693 #undef NMANTISSA
694 #undef NRANDI
695 #undef RANDU
696 
697 #define ZIGINT uint32_t
698 #define EMANTISSA 4294967296.0 /* 32 bit mantissa */
699 #define ERANDI randi32() /* 32 bits for mantissa */
700 #define NMANTISSA 2147483648.0 /* 31 bit mantissa */
701 #define NRANDI randi32() /* 31 bits for mantissa + 1 bit sign */
702 #define RANDU randu24()
703 
708 
710 {
711  int i;
712  float x, x1;
713 
714  /* Ziggurat tables for the normal distribution */
715  x1 = ZIGGURAT_NOR_R;
716  fwi[255] = x1 / NMANTISSA;
717  ffi[255] = exp (-0.5 * x1 * x1);
718 
719  /* Index zero is special for tail strip, where Marsaglia and Tsang
720  * defines this as
721  * k_0 = 2^31 * r * f(r) / v, w_0 = 0.5^31 * v / f(r), f_0 = 1,
722  * where v is the area of each strip of the ziggurat.
723  */
724  fki[0] = static_cast<ZIGINT> (x1 * ffi[255] / NOR_SECTION_AREA * NMANTISSA);
725  fwi[0] = NOR_SECTION_AREA / ffi[255] / NMANTISSA;
726  ffi[0] = 1.;
727 
728  for (i = 254; i > 0; i--)
729  {
730  /* New x is given by x = f^{-1}(v/x_{i+1} + f(x_{i+1})), thus
731  * need inverse operator of y = exp(-0.5*x*x) -> x = sqrt(-2*ln(y))
732  */
733  x = std::sqrt (-2. * std::log (NOR_SECTION_AREA / x1 + ffi[i+1]));
734  fki[i+1] = static_cast<ZIGINT> (x / x1 * NMANTISSA);
735  fwi[i] = x / NMANTISSA;
736  ffi[i] = exp (-0.5 * x * x);
737  x1 = x;
738  }
739 
740  fki[1] = 0;
741 
742  /* Zigurrat tables for the exponential distribution */
743  x1 = ZIGGURAT_EXP_R;
744  fwe[255] = x1 / EMANTISSA;
745  ffe[255] = exp (-x1);
746 
747  /* Index zero is special for tail strip, where Marsaglia and Tsang
748  * defines this as
749  * k_0 = 2^32 * r * f(r) / v, w_0 = 0.5^32 * v / f(r), f_0 = 1,
750  * where v is the area of each strip of the ziggurat.
751  */
752  fke[0] = static_cast<ZIGINT> (x1 * ffe[255] / EXP_SECTION_AREA * EMANTISSA);
753  fwe[0] = EXP_SECTION_AREA / ffe[255] / EMANTISSA;
754  ffe[0] = 1.;
755 
756  for (i = 254; i > 0; i--)
757  {
758  /* New x is given by x = f^{-1}(v/x_{i+1} + f(x_{i+1})), thus
759  * need inverse operator of y = exp(-x) -> x = -ln(y)
760  */
761  x = - std::log (EXP_SECTION_AREA / x1 + ffe[i+1]);
762  fke[i+1] = static_cast<ZIGINT> (x / x1 * EMANTISSA);
763  fwe[i] = x / EMANTISSA;
764  ffe[i] = exp (-x);
765  x1 = x;
766  }
767  fke[1] = 0;
768 
769  inittf = 0;
770 }
771 
772 /*
773  * Here is the guts of the algorithm. As Marsaglia and Tsang state the
774  * algorithm in their paper
775  *
776  * 1) Calculate a random signed integer j and let i be the index
777  * provided by the rightmost 8-bits of j
778  * 2) Set x = j * w_i. If j < k_i return x
779  * 3) If i = 0, then return x from the tail
780  * 4) If [f(x_{i-1}) - f(x_i)] * U < f(x) - f(x_i), return x
781  * 5) goto step 1
782  *
783  * Where f is the functional form of the distribution, which for a normal
784  * distribution is exp(-0.5*x*x)
785  */
786 
787 template <> OCTAVE_API float rand_normal<float> (void)
788 {
789  if (inittf)
791 
792  while (1)
793  {
794  /* 32-bit mantissa */
795  const uint32_t r = randi32 ();
796  const uint32_t rabs = r & LMASK;
797  const int idx = static_cast<int> (r & 0xFF);
798  const float x = static_cast<int32_t> (r) * fwi[idx];
799  if (rabs < fki[idx])
800  return x; /* 99.3% of the time we return here 1st try */
801  else if (idx == 0)
802  {
803  /* As stated in Marsaglia and Tsang
804  *
805  * For the normal tail, the method of Marsaglia[5] provides:
806  * generate x = -ln(U_1)/r, y = -ln(U_2), until y+y > x*x,
807  * then return r+x. Except that r+x is always in the positive
808  * tail!!!! Any thing random might be used to determine the
809  * sign, but as we already have r we might as well use it
810  *
811  * [PAK] but not the bottom 8 bits, since they are all 0 here!
812  */
813  float xx, yy;
814  do
815  {
816  xx = - ZIGGURAT_NOR_INV_R * std::log (RANDU);
817  yy = - std::log (RANDU);
818  }
819  while ( yy+yy <= xx*xx);
820  return ((rabs & 0x100) ? -ZIGGURAT_NOR_R-xx : ZIGGURAT_NOR_R+xx);
821  }
822  else if ((ffi[idx-1] - ffi[idx]) * RANDU + ffi[idx] < exp (-0.5*x*x))
823  return x;
824  }
825 }
826 
827 template <> OCTAVE_API float rand_exponential<float> (void)
828 {
829  if (inittf)
831 
832  while (1)
833  {
834  ZIGINT ri = ERANDI;
835  const int idx = static_cast<int> (ri & 0xFF);
836  const float x = ri * fwe[idx];
837  if (ri < fke[idx])
838  return x; /* 98.9% of the time we return here 1st try */
839  else if (idx == 0)
840  {
841  /* As stated in Marsaglia and Tsang
842  *
843  * For the exponential tail, the method of Marsaglia[5] provides:
844  * x = r - ln(U);
845  */
846  return ZIGGURAT_EXP_R - std::log (RANDU);
847  }
848  else if ((ffe[idx-1] - ffe[idx]) * RANDU + ffe[idx] < exp (-x))
849  return x;
850  }
851 }
852 
853 template <> OCTAVE_API void rand_uniform (octave_idx_type n, float *p)
854 {
855  std::generate_n (p, n, [](void) { return rand_uniform<float> (); });
856 }
857 
858 template <> OCTAVE_API void rand_normal (octave_idx_type n, float *p)
859 {
860  std::generate_n (p, n, [](void) { return rand_normal<float> (); });
861 }
862 
863 template <> OCTAVE_API void rand_exponential (octave_idx_type n, float *p)
864 {
865  std::generate_n (p, n, [](void) { return rand_exponential<float> (); });
866 }
867 
869 
OCTAVE_END_NAMESPACE(octave)
charNDArray min(char d, const charNDArray &m)
Definition: chNDArray.cc:207
OCTAVE_BEGIN_NAMESPACE(octave) static octave_value daspk_fcn
F77_RET_T const F77_DBLE * x
#define OCTAVE_API
Definition: main.in.cc:55
octave_idx_type n
Definition: mx-inlines.cc:753
T * r
Definition: mx-inlines.cc:773
pid_t getpid(void)
#define TWIST(u, v)
Definition: randmtzig.cc:190
static uint32_t * next
Definition: randmtzig.cc:192
static uint64_t ke[256]
Definition: randmtzig.cc:465
static double we[256]
Definition: randmtzig.cc:466
void get_mersenne_twister_state(uint32_t *save)
Definition: randmtzig.cc:318
static float ffe[256]
Definition: randmtzig.cc:707
#define ZIGGURAT_EXP_R
Definition: randmtzig.cc:452
static int initt
Definition: randmtzig.cc:196
static uint64_t ki[256]
Definition: randmtzig.cc:463
static uint32_t fke[256]
Definition: randmtzig.cc:706
void create_ziggurat_tables(void)
Definition: randmtzig.cc:506
void set_mersenne_twister_state(const uint32_t *save)
Definition: randmtzig.cc:311
static uint32_t fki[256]
Definition: randmtzig.cc:704
static double fe[256]
Definition: randmtzig.cc:466
static float fwe[256]
Definition: randmtzig.cc:707
#define EMANTISSA
Definition: randmtzig.cc:698
#define ZIGGURAT_TABLE_SIZE
Definition: randmtzig.cc:446
#define randi32
Definition: randmtzig.cc:367
static void create_ziggurat_float_tables(void)
Definition: randmtzig.cc:709
static double randu53(void)
Definition: randmtzig.cc:414
static uint64_t randi53(void)
Definition: randmtzig.cc:369
#define RANDU
Definition: randmtzig.cc:702
OCTAVE_API void rand_exponential(octave_idx_type n, double *p)
Definition: randmtzig.cc:685
static void next_state(void)
Definition: randmtzig.cc:324
#define ZIGINT
Definition: randmtzig.cc:697
OCTAVE_API double rand_uniform< double >(void)
Definition: randmtzig.cc:431
static double wi[256]
Definition: randmtzig.cc:464
void init_mersenne_twister(const uint32_t s)
Definition: randmtzig.cc:200
#define LMASK
Definition: randmtzig.cc:188
static uint64_t randi54(void)
Definition: randmtzig.cc:384
static uint32_t randmt(void)
Definition: randmtzig.cc:349
#define NRANDI
Definition: randmtzig.cc:701
#define ERANDI
Definition: randmtzig.cc:699
OCTAVE_API float rand_exponential< float >(void)
Definition: randmtzig.cc:827
#define NOR_SECTION_AREA
Definition: randmtzig.cc:450
static float randu24(void)
Definition: randmtzig.cc:400
OCTAVE_API void rand_uniform(octave_idx_type n, float *p)
Definition: randmtzig.cc:853
static uint32_t state[624]
Definition: randmtzig.cc:193
OCTAVE_API float rand_normal< float >(void)
Definition: randmtzig.cc:787
#define ZIGGURAT_NOR_R
Definition: randmtzig.cc:448
#define ZIGGURAT_NOR_INV_R
Definition: randmtzig.cc:449
#define UMASK
Definition: randmtzig.cc:187
#define NMANTISSA
Definition: randmtzig.cc:700
static double fi[256]
Definition: randmtzig.cc:464
OCTAVE_API float rand_uniform< float >(void)
Definition: randmtzig.cc:439
static float fwi[256]
Definition: randmtzig.cc:705
OCTAVE_API double rand_normal< double >(void)
Definition: randmtzig.cc:585
static int left
Definition: randmtzig.cc:194
static float ffi[256]
Definition: randmtzig.cc:705
static int initf
Definition: randmtzig.cc:195
#define MT_M
Definition: randmtzig.cc:185
static int inittf
Definition: randmtzig.cc:197
OCTAVE_API double rand_exponential< double >(void)
Definition: randmtzig.cc:649
OCTAVE_API void rand_normal(octave_idx_type n, double *p)
Definition: randmtzig.cc:680
#define EXP_SECTION_AREA
Definition: randmtzig.cc:454
#define MT_N
Definition: randmtzig.h:72