Geant4 Cross Reference

Cross-Referencing   Geant4
Geant4/externals/g4tools/include/tools/rtausmeui

Version: [ ReleaseNotes ] [ 1.0 ] [ 1.1 ] [ 2.0 ] [ 3.0 ] [ 3.1 ] [ 3.2 ] [ 4.0 ] [ 4.0.p1 ] [ 4.0.p2 ] [ 4.1 ] [ 4.1.p1 ] [ 5.0 ] [ 5.0.p1 ] [ 5.1 ] [ 5.1.p1 ] [ 5.2 ] [ 5.2.p1 ] [ 5.2.p2 ] [ 6.0 ] [ 6.0.p1 ] [ 6.1 ] [ 6.2 ] [ 6.2.p1 ] [ 6.2.p2 ] [ 7.0 ] [ 7.0.p1 ] [ 7.1 ] [ 7.1.p1 ] [ 8.0 ] [ 8.0.p1 ] [ 8.1 ] [ 8.1.p1 ] [ 8.1.p2 ] [ 8.2 ] [ 8.2.p1 ] [ 8.3 ] [ 8.3.p1 ] [ 8.3.p2 ] [ 9.0 ] [ 9.0.p1 ] [ 9.0.p2 ] [ 9.1 ] [ 9.1.p1 ] [ 9.1.p2 ] [ 9.1.p3 ] [ 9.2 ] [ 9.2.p1 ] [ 9.2.p2 ] [ 9.2.p3 ] [ 9.2.p4 ] [ 9.3 ] [ 9.3.p1 ] [ 9.3.p2 ] [ 9.4 ] [ 9.4.p1 ] [ 9.4.p2 ] [ 9.4.p3 ] [ 9.4.p4 ] [ 9.5 ] [ 9.5.p1 ] [ 9.5.p2 ] [ 9.6 ] [ 9.6.p1 ] [ 9.6.p2 ] [ 9.6.p3 ] [ 9.6.p4 ] [ 10.0 ] [ 10.0.p1 ] [ 10.0.p2 ] [ 10.0.p3 ] [ 10.0.p4 ] [ 10.1 ] [ 10.1.p1 ] [ 10.1.p2 ] [ 10.1.p3 ] [ 10.2 ] [ 10.2.p1 ] [ 10.2.p2 ] [ 10.2.p3 ] [ 10.3 ] [ 10.3.p1 ] [ 10.3.p2 ] [ 10.3.p3 ] [ 10.4 ] [ 10.4.p1 ] [ 10.4.p2 ] [ 10.4.p3 ] [ 10.5 ] [ 10.5.p1 ] [ 10.6 ] [ 10.6.p1 ] [ 10.6.p2 ] [ 10.6.p3 ] [ 10.7 ] [ 10.7.p1 ] [ 10.7.p2 ] [ 10.7.p3 ] [ 10.7.p4 ] [ 11.0 ] [ 11.0.p1 ] [ 11.0.p2 ] [ 11.0.p3, ] [ 11.0.p4 ] [ 11.1 ] [ 11.1.1 ] [ 11.1.2 ] [ 11.1.3 ] [ 11.2 ] [ 11.2.1 ] [ 11.2.2 ] [ 11.3.0 ]

  1 // Copyright (C) 2010, Guy Barrand. All rights reserved.
  2 // See the file tools.license for terms.
  3 
  4 #ifndef tools_rtausmeui
  5 #define tools_rtausmeui
  6 
  7 // G.Barrand : not so clear if 0 and tools::uint32_max() are included.
  8 //             A simple program shows that "if(r.shoot()==tools::uint32_max())" shows hits.
  9 //             (But we did not see hits for "if(r.shoot()==0)"). (See tools/tests/rand.cpp).
 10 
 11 // tausme is for Tausworthe maxmally equidistributed.
 12 
 13 // From logic and code of CERN-ROOT/TRandom2 class.
 14 
 15 // Random number generator class based on the maximally quidistributed combined
 16 // Tausworthe generator by L'Ecuyer.
 17 //
 18 // The period of the generator is 2**88 (about 10**26) and it uses only 3 words
 19 // for the state.
 20 //
 21 // For more information see:
 22 // P. L'Ecuyer, Mathematics of Computation, 65, 213 (1996)
 23 // P. L'Ecuyer, Mathematics of Computation, 68, 225 (1999)
 24 //
 25 // The publication are available online at
 26 //  http://www.iro.umontreal.ca/~lecuyer/myftp/papers/tausme.ps
 27 //  http://www.iro.umontreal.ca/~lecuyer/myftp/papers/tausme2.ps
 28 
 29 #ifdef TOOLS_MEM
 30 #include "mem"
 31 #include "S_STRING"
 32 #endif
 33 
 34 namespace tools {
 35 
 36 class rtausmeui {
 37 #ifdef TOOLS_MEM
 38   TOOLS_SCLASS(tools::rtausmeui)
 39 #endif
 40 public:
 41   rtausmeui(unsigned int a_seed = 1):m_seed(0),m_seed1(0),m_seed2(0){
 42 #ifdef TOOLS_MEM
 43     mem::increment(s_class().c_str());
 44 #endif
 45     set_seed(a_seed);
 46   }
 47   virtual ~rtausmeui(){
 48 #ifdef TOOLS_MEM
 49     mem::decrement(s_class().c_str());
 50 #endif
 51   }
 52 public:
 53   rtausmeui(const rtausmeui& a_from):m_seed(a_from.m_seed),m_seed1(a_from.m_seed1),m_seed2(a_from.m_seed2){
 54 #ifdef TOOLS_MEM
 55     mem::increment(s_class().c_str());
 56 #endif
 57   }
 58   rtausmeui& operator=(const rtausmeui& a_from) {
 59     m_seed = a_from.m_seed;
 60     m_seed1 = a_from.m_seed1;
 61     m_seed2 = a_from.m_seed2;
 62     return *this;
 63   }
 64 public:
 65   void set_seed(unsigned int a_seed) {
 66     m_seed = a_seed?a_seed:1;
 67 
 68     // Generate m_seed[1,2] needed for the generator state using
 69     // a linear congruential generator
 70     // The only condition, stated at the end of the 1999 L'Ecuyer paper is that the seeds
 71     // must be greater than 1,7 and 15.
 72 
 73     m_seed = LCG(m_seed);
 74     if (m_seed < 2) m_seed += 2UL;
 75     m_seed1 = LCG(m_seed);
 76     if (m_seed1 < 8) m_seed1 += 8UL;
 77     m_seed2 = LCG(m_seed1);
 78     if (m_seed2 < 16) m_seed2 += 16UL;
 79 
 80     // "warm it up" by calling it 6 times
 81     for (unsigned int i = 0; i < 6; ++i) shoot();
 82   }
 83   unsigned int seed() const {return m_seed;}
 84 
 85   unsigned int shoot() {
 86     //  TausWorth generator from L'Ecuyer, uses as seed 3x32bits integers
 87     //  Use a mask of 0xffffffffUL to make in work on 64 bit machines
 88     //  Periodicity of about  10**26
 89 
 90     unsigned int y;
 91 
 92     do {
 93       m_seed  = TAUSWORTHE (m_seed, 13, 19, 4294967294UL, 12);
 94       m_seed1 = TAUSWORTHE (m_seed1, 2, 25, 4294967288UL, 4);
 95       m_seed2 = TAUSWORTHE (m_seed2, 3, 11, 4294967280UL, 17);
 96 
 97       y = m_seed ^ m_seed1 ^ m_seed2;
 98     } while(!y);
 99 
100     return y;
101   }
102 protected:
103   static unsigned int LCG(unsigned int a_n) {
104     return ((69069 * a_n) & 0xffffffffUL);  // linear congurential generator
105   }
106   static unsigned int TAUSWORTHE(unsigned int a_s,unsigned int a_a,unsigned int a_b,unsigned int a_c,unsigned int a_d) {
107     return (((a_s & a_c) << a_d) & 0xffffffffUL ) ^ ((((a_s << a_a) & 0xffffffffUL )^ a_s) >> a_b);
108   }
109 protected:
110   unsigned int m_seed;
111   unsigned int m_seed1;
112   unsigned int m_seed2;
113 };
114 
115 }
116 
117 #endif