src/core/random-variable.cc
changeset 4218 debf1a8a96d3
parent 3679 07fdb67e52bb
child 4223 86a97665dcb0
--- a/src/core/random-variable.cc	Tue Dec 30 11:35:31 2008 -0800
+++ b/src/core/random-variable.cc	Tue Jan 13 17:15:44 2009 -0500
@@ -16,6 +16,7 @@
 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 //
 // Author: Rajib Bhattacharjea<raj.b@gatech.edu>
+// Author: Hadi Arbabi<marbabi@cs.odu.edu>
 //
 
 #include <iostream>
@@ -41,6 +42,78 @@
 namespace ns3{
 
 //-----------------------------------------------------------------------------
+// Seed Manager
+//-----------------------------------------------------------------------------
+
+uint32_t SeedManager::seed_[6]={1,2,3,4,5,6};
+bool     SeedManager::seedSet=false;
+uint32_t SeedManager::runNumber=0;
+
+void SeedManager::SetSeed(uint32_t seed[6])
+{
+	  if (SeedManager::seedSet)
+	  {
+	      cerr << "Seed Manager already set!" << endl;
+	      cerr << "Call to SeedManager::SetSeed(...) ignored" << endl;
+	      return;
+	  }
+	  SeedManager::seed_[0]=seed[0];
+	  SeedManager::seed_[1]=seed[1];
+	  SeedManager::seed_[2]=seed[2];
+	  SeedManager::seed_[3]=seed[3];
+	  SeedManager::seed_[4]=seed[4];
+	  SeedManager::seed_[5]=seed[5];
+	  if (!RngStream::CheckSeed(SeedManager::seed_))
+	    NS_FATAL_ERROR("Invalid seed");
+	  
+	  SeedManager::seedSet = true;
+}
+
+void SeedManager::GetSeed(uint32_t seed[6])
+{
+    for (int i=0; i<6; i++) 
+    {
+            seed[i] = seed_[i];
+    }
+}
+
+void SeedManager::SetSeed(uint32_t seed)
+{
+	uint32_t s[6];
+	s[0]=s[1]=s[2]=s[3]=s[4]=s[5]=seed;
+	SetSeed(s);
+}
+
+uint32_t SeedManager::GetSeed()
+{
+	uint32_t s[6];
+	GetSeed(s);
+	return s[0];
+}
+
+void SeedManager::SetRun(uint32_t run)
+{
+	runNumber=run;
+}
+
+uint32_t SeedManager::GetRun()
+{
+	return runNumber; 
+}
+
+bool SeedManager::CheckSeed (uint32_t seed)
+{
+	uint32_t s[6]; 
+	s[0]=s[1]=s[2]=s[3]=s[4]=s[5]=seed;
+	return RngStream::CheckSeed(s);
+}
+
+bool SeedManager::CheckSeed (uint32_t seed[6])
+{
+	return RngStream::CheckSeed(seed);
+}
+
+//-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
 // RandomVariableBase methods
 
@@ -54,63 +127,24 @@
   virtual double  GetValue() = 0;
   virtual uint32_t GetInteger();
   virtual RandomVariableBase*   Copy(void) const = 0;
-  virtual void GetSeed(uint32_t seed[6]);
 
-  static  void UseDevRandom(bool udr = true);
-  static void UseGlobalSeed(uint32_t s0, uint32_t s1, uint32_t s2, 
-                            uint32_t s3, uint32_t s4, uint32_t s5);
-  static void SetRunNumber(uint32_t n);
-private:
-  static void GetRandomSeeds(uint32_t seeds[6]);
-private:
-  static bool useDevRandom;    // True if using /dev/random desired
-  static bool globalSeedSet;   // True if global seed has been specified
-  static int  devRandom;       // File handle for /dev/random
-  static uint32_t globalSeed[6]; // The global seed to use
-  friend class RandomVariableInitializer;
 protected:
-  static unsigned long heuristic_sequence;
-  static RngStream* m_static_generator;
-  static uint32_t runNumber;
   static void Initialize();    // Initialize  the RNG system
   static bool initialized;     // True if package seed is set 
   RngStream* m_generator;  //underlying generator being wrapped
 };
 
-
-
 bool          RandomVariableBase::initialized = false;   // True if RngStream seed set 
-bool          RandomVariableBase::useDevRandom = false;  // True if use /dev/random
-bool          RandomVariableBase::globalSeedSet = false; // True if GlobalSeed called
-int           RandomVariableBase::devRandom = -1;
-uint32_t      RandomVariableBase::globalSeed[6];
-unsigned long RandomVariableBase::heuristic_sequence;
-RngStream*    RandomVariableBase::m_static_generator = 0;
-uint32_t      RandomVariableBase::runNumber = 0;
 
-//the static object random_variable_initializer initializes the static members
-//of RandomVariable
-static class RandomVariableInitializer
-{
-  public:
-  RandomVariableInitializer()
-  {
-//     RandomVariableBase::Initialize(); // sets the static package seed
-//     RandomVariableBase::m_static_generator = new RngStream();
-//     RandomVariableBase::m_static_generator->InitializeStream();
-  }
-  ~RandomVariableInitializer()
-  {
-    delete RandomVariableBase::m_static_generator;
-  }
-} random_variable_initializer;
 
 RandomVariableBase::RandomVariableBase() 
   : m_generator(NULL)
 {
-//   m_generator = new RngStream();
-//   m_generator->InitializeStream();
-//   m_generator->ResetNthSubstream(RandomVariableBase::runNumber);
+	 // it's better to be initialzed first and then set run number, 
+	 // it happens in GetValue() automatically
+	 //m_generator = new RngStream();
+     //m_generator->InitializeStream();
+     //m_generator->ResetNthSubstream(SeedManager::GetRun());
 }
 
 RandomVariableBase::RandomVariableBase(const RandomVariableBase& r)
@@ -132,115 +166,16 @@
   return (uint32_t)GetValue();
 }
 
-void RandomVariableBase::UseDevRandom(bool udr) 
-{
-  RandomVariableBase::useDevRandom = udr;
-}
-
-void RandomVariableBase::GetSeed(uint32_t seed[6])
-{
-  if(!m_generator)
-  {
-    m_generator = new RngStream();
-    m_generator->InitializeStream();
-    m_generator->ResetNthSubstream(RandomVariableBase::runNumber);
-  }
-  m_generator->GetState(seed);
-}
-
-//-----------------------------------------------------------------------------
-//-----------------------------------------------------------------------------
-// RandomVariableBase static methods
-void RandomVariableBase::UseGlobalSeed(uint32_t s0, uint32_t s1, uint32_t s2, 
-                                   uint32_t s3, uint32_t s4, uint32_t s5)
-{
-  if (RandomVariableBase::globalSeedSet)
-    {
-      NS_FATAL_ERROR ("Random number generator already initialized! "
-                      "Call to RandomVariableBase::UseGlobalSeed() ignored");
-    }
-  RandomVariableBase::globalSeed[0] = s0;
-  RandomVariableBase::globalSeed[1] = s1;
-  RandomVariableBase::globalSeed[2] = s2;
-  RandomVariableBase::globalSeed[3] = s3;
-  RandomVariableBase::globalSeed[4] = s4;
-  RandomVariableBase::globalSeed[5] = s5;
-  if (!RngStream::CheckSeed(RandomVariableBase::globalSeed))
-    NS_FATAL_ERROR("Invalid seed");
-  
-  RandomVariableBase::globalSeedSet = true;
-}
-
 void RandomVariableBase::Initialize()
 { 
+  uint32_t s[6];
   if (RandomVariableBase::initialized) return; // Already initialized and seeded
   RandomVariableBase::initialized = true;
-  if (!RandomVariableBase::globalSeedSet)
-    { // No global seed, try a random one
-      GetRandomSeeds(globalSeed);
-    }
-  // Seed the RngStream package
-  RngStream::SetPackageSeed(globalSeed);
+  SeedManager::GetSeed(s);
+  RngStream::SetPackageSeed(s);
 }
 
-void RandomVariableBase::GetRandomSeeds(uint32_t seeds[6])
-{
-  // Check if /dev/random exists
-  if (RandomVariableBase::useDevRandom && RandomVariableBase::devRandom < 0)
-    {
-      RandomVariableBase::devRandom = open("/dev/random", O_RDONLY);
-    }
-  if (RandomVariableBase::devRandom > 0)
-    { // Use /dev/random
-      while(true)
-        {
-          for (int i = 0; i < 6; ++i)
-            {
-              ssize_t bytes_read = read (RandomVariableBase::devRandom,
-                                         &seeds[i], sizeof (seeds[i]));
-              if (bytes_read != sizeof (seeds[i]))
-                {
-                  NS_FATAL_ERROR ("Read from /dev/random failed");
-                }
-            }
-          if (RngStream::CheckSeed(seeds)) break; // Got a valid one
-        }
-    }
-  else
-    { // Seed from time of day (code borrowed from ns2 random seeding)
-      // Thanks to John Heidemann for this technique
-      while(true)
-        {
-          timeval tv;
-          gettimeofday(&tv, 0);
-          seeds[0] = (tv.tv_sec^tv.tv_usec^(++heuristic_sequence <<8))
-              & 0x7fffffff;
-          gettimeofday(&tv, 0);
-          seeds[1] = (tv.tv_sec^tv.tv_usec^(++heuristic_sequence <<8))
-              & 0x7fffffff;
-          gettimeofday(&tv, 0);
-          seeds[2] = (tv.tv_sec^tv.tv_usec^(++heuristic_sequence <<8))
-              & 0x7fffffff;
-          gettimeofday(&tv, 0);
-          seeds[3] = (tv.tv_sec^tv.tv_usec^(++heuristic_sequence <<8))
-              & 0x7fffffff;
-          gettimeofday(&tv, 0);
-          seeds[4] = (tv.tv_sec^tv.tv_usec^(++heuristic_sequence <<8))
-              & 0x7fffffff;
-          gettimeofday(&tv, 0);
-          seeds[5] = (tv.tv_sec^tv.tv_usec^(++heuristic_sequence <<8))
-              & 0x7fffffff;
-          if (RngStream::CheckSeed(seeds)) break; // Got a valid one
-        }
-    }
-}
-
-void RandomVariableBase::SetRunNumber(uint32_t n)
-{
-  runNumber = n;
-}
-
-
+//-------------------------------------------------------
 
 RandomVariable::RandomVariable()
   : m_variable (0)
@@ -277,33 +212,14 @@
 {
   return m_variable->GetInteger ();
 }
-void 
-RandomVariable::GetSeed(uint32_t seed[6]) const
-{
-  return m_variable->GetSeed (seed);
-}
-void 
-RandomVariable::UseDevRandom(bool udr)
-{
-  RandomVariableBase::UseDevRandom (udr);
-}
-void 
-RandomVariable::UseGlobalSeed(uint32_t s0, uint32_t s1, uint32_t s2, 
-                              uint32_t s3, uint32_t s4, uint32_t s5)
-{
-  RandomVariableBase::UseGlobalSeed (s0, s1, s2, s3, s4, s5);
-}
-void 
-RandomVariable::SetRunNumber(uint32_t n)
-{
-  RandomVariableBase::SetRunNumber (n);
-}
+
 RandomVariableBase *
 RandomVariable::Peek (void) const
 {
   return m_variable;
 }
 
+
 ATTRIBUTE_VALUE_IMPLEMENT (RandomVariable);
 ATTRIBUTE_CHECKER_IMPLEMENT (RandomVariable);
 
@@ -335,15 +251,14 @@
    * \return A value between low and high values specified by the constructor
    */
   virtual double GetValue();
+
+  /**
+   * \return A value between low and high values specified by parameters
+   */
+  virtual double GetValue(double s, double l);
+  
   virtual RandomVariableBase*  Copy(void) const;
 
-public:
-  /**
-   * \param s Low end of the range
-   * \param l High end of the range
-   * \return A uniformly distributed random number between s and l
-   */
-  static double GetSingleValue(double s, double l);
 private:
   double m_min;
   double m_max;
@@ -380,37 +295,46 @@
   {
     m_generator = new RngStream();
     m_generator->InitializeStream();
-    m_generator->ResetNthSubstream(RandomVariableBase::runNumber);
+    m_generator->ResetNthSubstream(SeedManager::GetRun());
   }
   return m_min + m_generator->RandU01() * (m_max - m_min);
 }
 
+double UniformVariableImpl::GetValue(double s, double l) 
+{
+	  if(!RandomVariableBase::initialized)
+	  {
+	    RandomVariableBase::Initialize();
+	  }
+	  if(!m_generator)
+	  {
+	    m_generator = new RngStream();
+	    m_generator->InitializeStream();
+	    m_generator->ResetNthSubstream(SeedManager::GetRun());
+	  }
+	  return s + m_generator->RandU01() * (l-s); 
+}
+
 RandomVariableBase* UniformVariableImpl::Copy() const
 {
   return new UniformVariableImpl(*this);
 }
 
-double UniformVariableImpl::GetSingleValue(double s, double l)
-{
-  if(!RandomVariableBase::m_static_generator)
-  {
-    RandomVariableBase::Initialize(); // sets the static package seed
-    RandomVariableBase::m_static_generator = new RngStream();
-    RandomVariableBase::m_static_generator->InitializeStream();
-  }
-  return s + m_static_generator->RandU01() * (l - s);;
-}
-
 UniformVariable::UniformVariable()
   : RandomVariable (UniformVariableImpl ())
 {}
 UniformVariable::UniformVariable(double s, double l)
   : RandomVariable (UniformVariableImpl (s, l))
 {}
-double 
-UniformVariable::GetSingleValue(double s, double l)
+
+double UniformVariable::GetValue()
 {
-  return UniformVariableImpl::GetSingleValue (s, l);
+	return Peek()->GetValue();
+}
+
+double UniformVariable::GetValue(double s, double l)
+{
+  return ((UniformVariableImpl*)Peek())->GetValue(s,l);
 }
 
 
@@ -623,13 +547,7 @@
    */
   virtual double GetValue();
   virtual RandomVariableBase* Copy(void) const;
-public:
-  /**
-   * \param m The mean of the distribution from which the return value is drawn
-   * \param b The upper bound value desired, beyond which values get clipped
-   * \return A random number from an exponential distribution with mean m
-   */
-  static double GetSingleValue(double m, double b=0);
+
 private:
   double m_mean;  // Mean value of RV
   double m_bound; // Upper bound on value (if non-zero)
@@ -657,7 +575,7 @@
   {
     m_generator = new RngStream();
     m_generator->InitializeStream();
-    m_generator->ResetNthSubstream(RandomVariableBase::runNumber);
+    m_generator->ResetNthSubstream(SeedManager::GetRun());
   }
   double r = -m_mean*log(m_generator->RandU01());
   if (m_bound != 0 && r > m_bound) return m_bound;
@@ -668,18 +586,6 @@
 {
   return new ExponentialVariableImpl(*this);
 }
-double ExponentialVariableImpl::GetSingleValue(double m, double b/*=0*/)
-{
-  if(!RandomVariableBase::m_static_generator)
-  {
-    RandomVariableBase::Initialize(); // sets the static package seed
-    RandomVariableBase::m_static_generator = new RngStream();
-    RandomVariableBase::m_static_generator->InitializeStream();
-  }
-  double r = -m*log(m_static_generator->RandU01());
-  if (b != 0 && r > b) return b;
-  return r;
-}
 
 ExponentialVariable::ExponentialVariable()
   : RandomVariable (ExponentialVariableImpl ())
@@ -690,11 +596,6 @@
 ExponentialVariable::ExponentialVariable(double m, double b)
   : RandomVariable (ExponentialVariableImpl (m, b))
 {}
-double 
-ExponentialVariable::GetSingleValue(double m, double b)
-{
-  return ExponentialVariableImpl::GetSingleValue (m, b);
-}
 
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
@@ -743,17 +644,7 @@
    */
   virtual double GetValue();
   virtual RandomVariableBase* Copy() const;
-public:
-  /**
-   * \param m The mean value of the distribution from which the return value
-   * is drawn.
-   * \param s The shape parameter of the distribution from which the return
-   * value is drawn.
-   * \param b The upper bound to which to restrict return values
-   * \return A random number from a Pareto distribution with mean m and shape
-   * parameter s.
-   */
-  static double GetSingleValue(double m, double s, double b=0);
+
 private:
   double m_mean;  // Mean value of RV
   double m_shape; // Shape parameter
@@ -786,7 +677,7 @@
   {
     m_generator = new RngStream();
     m_generator->InitializeStream();
-    m_generator->ResetNthSubstream(RandomVariableBase::runNumber);
+    m_generator->ResetNthSubstream(SeedManager::GetRun());
   }
   double scale = m_mean * ( m_shape - 1.0) / m_shape;
   double r = (scale * ( 1.0 / pow(m_generator->RandU01(), 1.0 / m_shape)));
@@ -799,20 +690,6 @@
   return new ParetoVariableImpl(*this);
 }
 
-double ParetoVariableImpl::GetSingleValue(double m, double s, double b/*=0*/)
-{
-  if(!RandomVariableBase::m_static_generator)
-  {
-    RandomVariableBase::Initialize(); // sets the static package seed
-    RandomVariableBase::m_static_generator = new RngStream();
-    RandomVariableBase::m_static_generator->InitializeStream();
-  }
-  double scale = m * ( s - 1.0) / s;
-  double r = (scale * ( 1.0 / pow(m_static_generator->RandU01(), 1.0 / s)));
-  if (b != 0 && r > b) return b;
-  return r;
-}
-
 ParetoVariable::ParetoVariable ()
   : RandomVariable (ParetoVariableImpl ())
 {}
@@ -825,11 +702,6 @@
 ParetoVariable::ParetoVariable(double m, double s, double b)
   : RandomVariable (ParetoVariableImpl (m, s, b))
 {}
-double 
-ParetoVariable::GetSingleValue(double m, double s, double b)
-{
-  return ParetoVariableImpl::GetSingleValue (m, s, b);
-}
 
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
@@ -879,14 +751,7 @@
    */
   virtual double GetValue();
   virtual RandomVariableBase* Copy(void) const;
-public:
-  /**
-   * \param m Mean value for the distribution.
-   * \param s Shape (alpha) parameter for the distribution.
-   * \param b Upper limit on returned values
-   * \return Random number from a distribution specified by m,s, and b
-   */
-  static double GetSingleValue(double m, double s, double b=0);
+
 private:
   double m_mean;  // Mean value of RV
   double m_alpha; // Shape parameter
@@ -914,7 +779,7 @@
   {
     m_generator = new RngStream();
     m_generator->InitializeStream();
-    m_generator->ResetNthSubstream(RandomVariableBase::runNumber);
+    m_generator->ResetNthSubstream(SeedManager::GetRun());
   }
   double exponent = 1.0 / m_alpha;
   double r = m_mean * pow( -log(m_generator->RandU01()), exponent);
@@ -927,20 +792,6 @@
   return new WeibullVariableImpl(*this);
 }
 
-double WeibullVariableImpl::GetSingleValue(double m, double s, double b/*=0*/)
-{
-  if(!RandomVariableBase::m_static_generator)
-  {
-    RandomVariableBase::Initialize(); // sets the static package seed
-    RandomVariableBase::m_static_generator = new RngStream();
-    RandomVariableBase::m_static_generator->InitializeStream();
-  }
-  double exponent = 1.0 / s;
-  double r = m * pow( -log(m_static_generator->RandU01()), exponent);
-  if (b != 0 && r > b) return b;
-  return r;
-}
-
 WeibullVariable::WeibullVariable()
   : RandomVariable (WeibullVariableImpl ())
 {}
@@ -953,11 +804,7 @@
 WeibullVariable::WeibullVariable(double m, double s, double b)
   : RandomVariable (WeibullVariableImpl (m, s, b))
 {}
-double 
-WeibullVariable::GetSingleValue(double m, double s, double b)
-{
-  return WeibullVariableImpl::GetSingleValue (m, s, b);
-}
+
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
 // NormalVariableImpl methods
@@ -987,14 +834,7 @@
    */
   virtual double GetValue();
   virtual RandomVariableBase* Copy(void) const;
-public:
-  /**
-   * \param m Mean value
-   * \param v Variance
-   * \param b Bound.  The NormalVariableImpl is bounded within +-bound.
-   * \return A random number from a distribution specified by m,v, and b.
-   */ 
-  static double GetSingleValue(double m, double v, double b = INFINITE_VALUE);
+
 private:
   double m_mean;      // Mean value of RV
   double m_variance;  // Mean value of RV
@@ -1017,7 +857,7 @@
 
 NormalVariableImpl::NormalVariableImpl(const NormalVariableImpl& c)
   : RandomVariableBase(c), m_mean(c.m_mean), m_variance(c.m_variance),
-    m_bound(c.m_bound), m_nextValid(false) { }
+    m_bound(c.m_bound) { }
 
 double NormalVariableImpl::GetValue()
 {
@@ -1029,7 +869,7 @@
   {
     m_generator = new RngStream();
     m_generator->InitializeStream();
-    m_generator->ResetNthSubstream(RandomVariableBase::runNumber);
+    m_generator->ResetNthSubstream(SeedManager::GetRun());
   }
   if (m_nextValid)
     { // use previously generated
@@ -1049,21 +889,11 @@
         { // Got good pair
           double y = sqrt((-2 * log(w))/w);
           m_next = m_mean + v2 * y * sqrt(m_variance);
-          //if next is in bounds, it is valid
-          m_nextValid = fabs(m_next-m_mean) <= m_bound;
+          if (fabs(m_next) > m_bound) m_next = m_bound * (m_next)/fabs(m_next);
+          m_nextValid = true;
           double x1 = m_mean + v1 * y * sqrt(m_variance);
-          //if x1 is in bounds, return it
-          if (fabs(x1-m_mean) <= m_bound)
-          {
-            return x1;
-          }
-          //otherwise try and return m_next if it is valid
-          else if (m_nextValid)
-          {
-            m_nextValid = false;
-            return m_next;
-          }
-          //otherwise, just run this loop again
+          if (fabs(x1) > m_bound) x1 = m_bound * (x1)/fabs(x1);
+          return x1;
         }
     }
 }
@@ -1073,71 +903,12 @@
   return new NormalVariableImpl(*this);
 }
 
-double NormalVariableImpl::GetSingleValue(double m, double v, double b)
-{
-  if(!RandomVariableBase::m_static_generator)
-  {
-    RandomVariableBase::Initialize(); // sets the static package seed
-    RandomVariableBase::m_static_generator = new RngStream();
-    RandomVariableBase::m_static_generator->InitializeStream();
-  }
-  if (m_static_nextValid)
-    { // use previously generated
-      m_static_nextValid = false;
-      return m_static_next;
-    }
-  while(1)
-    { // See Simulation Modeling and Analysis p. 466 (Averill Law)
-      // for algorithm; basically a Box-Muller transform:
-      // http://en.wikipedia.org/wiki/Box-Muller_transform
-      double u1 = m_static_generator->RandU01();
-      double u2 = m_static_generator->RandU01();;
-      double v1 = 2 * u1 - 1;
-      double v2 = 2 * u2 - 1;
-      double w = v1 * v1 + v2 * v2;
-      if (w <= 1.0)
-        { // Got good pair
-          double y = sqrt((-2 * log(w))/w);
-          m_static_next = m + v2 * y * sqrt(v);
-          //if next is in bounds, it is valid
-          m_static_nextValid = fabs(m_static_next-m) <= b;;
-          double x1 = m + v1 * y * sqrt(v);
-          //if x1 is in bounds, return it
-          if (fabs(x1-m) <= b)
-          {
-            return x1;
-          }
-          //otherwise try and return m_next if it is valid
-          else if (m_static_nextValid)
-          {
-            m_static_nextValid = false;
-            return m_static_next;
-          }
-          //otherwise, just run this loop again
-        }
-    }
-}
-
 NormalVariable::NormalVariable()
   : RandomVariable (NormalVariableImpl ())
 {}
-NormalVariable::NormalVariable(double m, double v)
-  : RandomVariable (NormalVariableImpl (m, v))
-{}
 NormalVariable::NormalVariable(double m, double v, double b)
   : RandomVariable (NormalVariableImpl (m, v, b))
 {}
-double 
-NormalVariable::GetSingleValue(double m, double v)
-{
-  return NormalVariableImpl::GetSingleValue (m, v);
-}
-double 
-NormalVariable::GetSingleValue(double m, double v, double b)
-{
-  return NormalVariableImpl::GetSingleValue (m, v, b);
-}
-
 
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
@@ -1208,7 +979,7 @@
   {
     m_generator = new RngStream();
     m_generator->InitializeStream();
-    m_generator->ResetNthSubstream(RandomVariableBase::runNumber);
+    m_generator->ResetNthSubstream(SeedManager::GetRun());
   }
   if (emp.size() == 0) return 0.0; // HuH? No empirical data
   if (!validated) Validate();      // Insure in non-decreasing
@@ -1395,13 +1166,7 @@
    */
   virtual double GetValue ();
   virtual RandomVariableBase* Copy(void) const;
-public:
-  /**
-   * \param mu mu parameter of the underlying normal distribution
-   * \param sigma sigma parameter of the underlying normal distribution
-   * \return A random number from the distribution specified by mu and sigma
-   */
-  static double GetSingleValue(double mu, double sigma);
+
 private:
   double m_mu;
   double m_sigma;
@@ -1455,7 +1220,7 @@
   {
     m_generator = new RngStream();
     m_generator->InitializeStream();
-    m_generator->ResetNthSubstream(RandomVariableBase::runNumber);
+    m_generator->ResetNthSubstream(SeedManager::GetRun());
   }
   double u, v, r2, normal, z;
 
@@ -1478,42 +1243,9 @@
   return z;
 }
 
-double LogNormalVariableImpl::GetSingleValue (double mu, double sigma)
-{
-  if(!RandomVariableBase::m_static_generator)
-  {
-    RandomVariableBase::Initialize(); // sets the static package seed
-    RandomVariableBase::m_static_generator = new RngStream();
-    RandomVariableBase::m_static_generator->InitializeStream();
-  }
-  double u, v, r2, normal, z;
-  do
-    {
-      /* choose x,y in uniform square (-1,-1) to (+1,+1) */
-      u = -1 + 2 * m_static_generator->RandU01 ();
-      v = -1 + 2 * m_static_generator->RandU01 ();
-
-      /* see if it is in the unit circle */
-      r2 = u * u + v * v;
-    }
-  while (r2 > 1.0 || r2 == 0);
-
-  normal = u * sqrt (-2.0 * log (r2) / r2);
-
-  z =  exp (sigma * normal + mu);
-
-  return z;
-}
-
 LogNormalVariable::LogNormalVariable (double mu, double sigma)
   : RandomVariable (LogNormalVariableImpl (mu, sigma))
 {}
-double 
-LogNormalVariable::GetSingleValue(double mu, double sigma)
-{
-  return LogNormalVariableImpl::GetSingleValue (mu, sigma);
-}
-
 
 //-----------------------------------------------------------------------------
 //-----------------------------------------------------------------------------
@@ -1542,14 +1274,7 @@
    */
   virtual double GetValue();
   virtual RandomVariableBase*  Copy(void) const;
-public:
-  /**
-   * \param s Low end of the range
-   * \param l High end of the range
-   * \param mean mean of the distribution
-   * \return A triangularly distributed random number between s and l
-   */
-  static double GetSingleValue(double s, double l, double mean);
+
 private:
   double m_min;
   double m_max;
@@ -1576,7 +1301,7 @@
   {
     m_generator = new RngStream();
     m_generator->InitializeStream();
-    m_generator->ResetNthSubstream(RandomVariableBase::runNumber);
+    m_generator->ResetNthSubstream(SeedManager::GetRun());
   }
   double u = m_generator->RandU01();
   if(u <= (m_mode - m_min) / (m_max - m_min) )
@@ -1590,33 +1315,12 @@
   return new TriangularVariableImpl(*this);
 }
 
-double TriangularVariableImpl::GetSingleValue(double s, double l, double mean)
-{
-  if(!RandomVariableBase::m_static_generator)
-  {
-    RandomVariableBase::Initialize(); // sets the static package seed
-    RandomVariableBase::m_static_generator = new RngStream();
-    RandomVariableBase::m_static_generator->InitializeStream();
-  }
-  double mode = 3.0*mean-s-l;
-  double u = m_static_generator->RandU01();
-  if(u <= (mode - s) / (l - s) )
-    return s + sqrt(u * (l - s) * (mode - s) );
-  else
-    return l - sqrt( (1-u) * (l - s) * (l - mode) );
-}
-
 TriangularVariable::TriangularVariable()
   : RandomVariable (TriangularVariableImpl ())
 {}
 TriangularVariable::TriangularVariable(double s, double l, double mean)
   : RandomVariable (TriangularVariableImpl (s,l,mean))
 {}
-double 
-TriangularVariable::GetSingleValue(double s, double l, double mean)
-{
-  return TriangularVariableImpl::GetSingleValue (s,l,mean);
-}
 
 
 std::ostream &operator << (std::ostream &os, const RandomVariable &var)
@@ -1691,112 +1395,3 @@
 
 }//namespace ns3
 
-
-#ifdef RUN_SELF_TESTS
-#include "test.h"
-#include <vector>
-
-namespace ns3 {
-
-
-class RandomVariableTest : public Test
-{
-public:
-  RandomVariableTest () : Test ("RandomVariable") {}
-  virtual bool RunTests (void)
-  {
-    bool result = true;
-    const double desired_mean = 1.0;
-    const double desired_stddev = 1.0;
-    double tmp = log (1 + (desired_stddev/desired_mean)*(desired_stddev/desired_mean));
-    double sigma = sqrt (tmp);
-    double mu = log (desired_mean) - 0.5*tmp;
-
-    // Test a custom lognormal instance
-    {
-      LogNormalVariable lognormal (mu, sigma);
-      vector<double> samples;
-      const int NSAMPLES = 10000;
-      double sum = 0;
-      for (int n = NSAMPLES; n; --n)
-        {
-          double value = lognormal.GetValue ();
-          sum += value;
-          samples.push_back (value);
-        }
-      double obtained_mean = sum / NSAMPLES;
-      sum = 0;
-      for (vector<double>::iterator iter = samples.begin (); iter != samples.end (); iter++)
-        {
-          double tmp = (*iter - obtained_mean);
-          sum += tmp*tmp;
-        }
-      double obtained_stddev = sqrt (sum / (NSAMPLES - 1));
-
-      if (not (obtained_mean/desired_mean > 0.90 and obtained_mean/desired_mean < 1.10))
-        {
-          result = false;
-          Failure () << "Obtained lognormal mean value " << obtained_mean << ", expected " << desired_mean << std::endl;
-        }
-
-      if (not (obtained_stddev/desired_stddev > 0.90 and obtained_stddev/desired_stddev < 1.10))
-        {
-          result = false;
-          Failure () << "Obtained lognormal stddev value " << obtained_stddev <<
-            ", expected " << desired_stddev << std::endl;
-        }
-    }
-
-    // Test GetSingleValue
-    {
-      vector<double> samples;
-      const int NSAMPLES = 10000;
-      double sum = 0;
-      for (int n = NSAMPLES; n; --n)
-        {
-          double value = LogNormalVariable::GetSingleValue (mu, sigma);
-          sum += value;
-          samples.push_back (value);
-        }
-      double obtained_mean = sum / NSAMPLES;
-      sum = 0;
-      for (vector<double>::iterator iter = samples.begin (); iter != samples.end (); iter++)
-        {
-          double tmp = (*iter - obtained_mean);
-          sum += tmp*tmp;
-        }
-      double obtained_stddev = sqrt (sum / (NSAMPLES - 1));
-
-      if (not (obtained_mean/desired_mean > 0.90 and obtained_mean/desired_mean < 1.10))
-        {
-          result = false;
-          Failure () << "Obtained LogNormalVariable::GetSingleValue mean value " << obtained_mean
-                     << ", expected " << desired_mean << std::endl;
-        }
-
-      if (not (obtained_stddev/desired_stddev > 0.90 and obtained_stddev/desired_stddev < 1.10))
-        {
-          result = false;
-          Failure () << "Obtained LogNormalVariable::GetSingleValue stddev value " << obtained_stddev <<
-            ", expected " << desired_stddev << std::endl;
-        }
-    }
-
-    // Test attribute serialization
-    {
-      RandomVariableValue val;
-      val.DeserializeFromString ("Uniform:0.1:0.2", MakeRandomVariableChecker ());
-      RandomVariable rng = val.Get ();
-      NS_TEST_ASSERT_EQUAL (val.SerializeToString (MakeRandomVariableChecker ()), "Uniform:0.1:0.2");
-    }
-
-    return result;
-  }
-};
-
-
-static RandomVariableTest g_random_variable_tests;
-
-}//namespace ns3
-
-#endif /* RUN_SELF_TESTS */