add BivariateCollector and passed its test suite draft
authorLi Li <ll024@bucknell.edu>
Tue, 29 Jul 2014 15:56:48 -0400
changeset 10565 525e085dda14
parent 10564 6b7366ca2b8a
child 10566 f34620a9e2a0
add BivariateCollector and passed its test suite
src/stats/model/basic-stats-collector.h
src/stats/model/bivariate-collector.cc
src/stats/model/bivariate-collector.h
src/stats/model/sum-collector.h
src/stats/test/bivariate-collector-test-suite.cc
src/stats/wscript
--- a/src/stats/model/basic-stats-collector.h	Thu Jul 24 18:05:49 2014 -0400
+++ b/src/stats/model/basic-stats-collector.h	Tue Jul 29 15:56:48 2014 -0400
@@ -25,7 +25,7 @@
 #ifndef BASIC_STATS_COLLECTOR_H
 #define BASIC_STATS_COLLECTOR_H
 
-#include "ns3/event-driven-collector.h"
+#include "ns3/collector.h"
 #include "ns3/object.h"
 #include "ns3/type-id.h"
 #include "ns3/traced-value.h"
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/stats/model/bivariate-collector.cc	Tue Jul 29 15:56:48 2014 -0400
@@ -0,0 +1,201 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2014 Bucknell University
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ * Author: Vinicius Daly Felizardo (vdf001@bucknell.edu)
+ *        Li Li (ll024@bucknell.edu)
+ * 	 
+ *
+ */
+
+#include "ns3/bivariate-collector.h"
+#include "ns3/object.h"
+#include "ns3/traced-value.h"
+#include "ns3/log.h"
+#include "ns3/simulator.h"
+#include "ns3/double.h"
+#include "ns3/integer.h"
+#include "ns3/uinteger.h"
+#include "ns3/log.h"
+
+NS_LOG_COMPONENT_DEFINE("BivariateCollector");
+
+namespace ns3{
+
+NS_OBJECT_ENSURE_REGISTERED (BivariateCollector);
+
+TypeId
+BivariateCollector::GetTypeId (void)
+{
+  static TypeId tid = TypeId ("ns3::BivariateCollector")
+    .SetParent<Collector> ()
+    .AddConstructor<BivariateCollector> ()
+    .AddTraceSource("Correlation",
+                    "The correlation of the data received from two trace sources",
+                    MakeTraceSourceAccessor(&BivariateCollector::m_outputCorrelation))
+    .AddTraceSource("Covariance",
+                    "The covariance of the data received from two trace sources",
+                    MakeTraceSourceAccessor(&BivariateCollector::m_outputCovariance))
+    ;
+    return tid;
+}
+
+BivariateCollector::BivariateCollector ()
+{
+  NS_LOG_FUNCTION(this);
+  Reset();
+}
+
+BivariateCollector::~BivariateCollector ()
+{
+  NS_LOG_FUNCTION(this);
+}
+
+void
+BivariateCollector::TraceSinkU (double oldData, double newData)
+{
+  NS_LOG_FUNCTION(this << oldData << newData);
+  if (!IsEnabled ())
+  {
+    NS_LOG_DEBUG("Collector not enabled");
+    return;
+  }
+
+  uQueue.push (newData);
+  CheckAndReportData();
+}
+
+void
+BivariateCollector::TraceSinkV (double oldData, double newData)
+{
+  NS_LOG_FUNCTION(this << oldData << newData);
+  if (!IsEnabled ())
+  {
+    NS_LOG_DEBUG("Collector not enabled");
+    return;
+  }
+
+  vQueue.push (newData);
+  CheckAndReportData();
+}
+
+void
+BivariateCollector::CheckAndReportData()
+{
+  NS_LOG_FUNCTION(this);
+  if ( (!uQueue.empty()) && (!vQueue.empty()) )
+  {
+    double u = uQueue.front();
+    double v = vQueue.front();
+
+    Update(u,v);
+    uQueue.pop();
+    vQueue.pop();
+
+    ReportData();
+  }
+}
+
+void
+BivariateCollector::DoReportData()
+{
+  NS_LOG_FUNCTION(this);
+
+  double time = Simulator::Now().GetSeconds();
+  double correlation = GetCorrelation();
+  double covariance = GetCovariance();
+
+  m_outputCorrelation(time, correlation);
+  m_outputCovariance(time, covariance);
+}
+
+void
+BivariateCollector::Update(double u, double v)
+{
+  NS_LOG_FUNCTION(this);
+  m_total++;
+
+  /***********************
+    Calculating covariance
+    As defined by Discrete-Event Simulation: A First course
+    (Leemis and Park) - Page 180 (Definition 4.4.3)
+    w_i = w_i-1 + ((i-1)/i) * (u - mean u) * (v - mean v)
+    cov = w_i / i
+   ***********************/
+
+  double diff_u = u - m_uCalculator.getMean();
+  double diff_v = v - m_vCalculator.getMean();
+
+  double temp = (m_total - 1.0) / m_total;
+
+  if (m_total>1) {
+    m_cosum += diff_u * diff_v * temp;    
+    m_sum_u  += diff_u * diff_u * temp;
+    m_sum_v  += diff_v * diff_v * temp;
+  }
+
+  m_uCalculator.Update(u);
+  m_vCalculator.Update(v);
+}
+
+
+double
+BivariateCollector::GetCorrelation() 
+{
+  NS_LOG_FUNCTION(this);
+  if (m_total==0)
+    return 0;
+
+  double stdev_u    = sqrt(m_sum_u / m_total);
+  double stdev_v    = sqrt(m_sum_v / m_total);
+  double stdDevDenom = (stdev_u * stdev_v);
+  /***********************
+    Calculating correlation
+    (corr = cov / (stdDevA * stdDevB))
+   ***********************/
+  double correlation;
+  if (stdDevDenom > 0.0) {
+    correlation = (m_cosum/m_total) / stdDevDenom;
+  } else {
+    correlation = 0.0;
+  }
+  return correlation;
+}
+
+double
+BivariateCollector::GetCovariance()
+{
+  NS_LOG_FUNCTION(this);
+  double correlation = GetCorrelation();
+  double covariance = correlation * m_uCalculator.getStddev() * m_vCalculator.getStddev();
+  return covariance;
+}
+
+
+void
+BivariateCollector::Reset () 
+{
+  NS_LOG_FUNCTION(this);
+  m_uCalculator.Reset();
+  m_vCalculator.Reset();
+  m_total=0;
+  m_cosum=0;
+  m_sum_u=0;
+  m_sum_v=0;
+}
+
+
+} // namespace ns3
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/stats/model/bivariate-collector.h	Tue Jul 29 15:56:48 2014 -0400
@@ -0,0 +1,75 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2014 Bucknell University
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ * Authors: Li Li (ll024@bucknell.edu)
+ *        Vinicius Daly Felizardo (vdf001@bucknell.edu) 
+ *
+ */
+
+#ifndef BIVARIATE_COLLECTOR_H
+#define BIVARIATE_COLLECTOR_H
+
+#include "ns3/collector.h"
+#include "ns3/object.h"
+#include "ns3/type-id.h"
+#include "ns3/traced-value.h"
+#include "ns3/basic-data-calculators.h"
+#include <queue>
+
+namespace ns3 {
+
+class BivariateCollector: public Collector
+{
+public:
+  static TypeId GetTypeId (void);
+
+  BivariateCollector ();
+  virtual ~BivariateCollector ();
+
+  void TraceSinkU (double oldData, double newData);
+  void TraceSinkV (double oldData, double newData);
+
+  void Update (double u, double v);
+  void Reset ();
+
+  double GetCorrelation ();
+  double GetCovariance ();
+
+protected:
+  virtual void DoReportData (void);
+
+private:
+  MinMaxAvgTotalCalculator<double> m_uCalculator; //In use to calculate average and stdev.
+  MinMaxAvgTotalCalculator<double> m_vCalculator; //In use to calculate average and stdev.
+
+  void CheckAndReportData();
+
+  std::queue<double> uQueue;
+  std::queue<double> vQueue;
+
+  uint32_t m_total;                          //Total of samples so far
+  double m_cosum;                            //Sum to calculate covariance
+  double m_sum_u;                            //Sum of u
+  double m_sum_v;                            //Sum of v
+
+  TracedCallback<double, double> m_outputCorrelation;
+  TracedCallback<double, double> m_outputCovariance;
+};
+
+} // namespace ns3
+
+#endif // BIVARIATE_COLLECTOR_H
--- a/src/stats/model/sum-collector.h	Thu Jul 24 18:05:49 2014 -0400
+++ b/src/stats/model/sum-collector.h	Tue Jul 29 15:56:48 2014 -0400
@@ -22,7 +22,7 @@
 #ifndef SUM_COLLECTOR_H
 #define SUM_COLLECTOR_H
 
-#include "ns3/event-driven-collector.h"
+#include "ns3/collector.h"
 #include "ns3/object.h"
 #include "ns3/type-id.h"
 #include "ns3/traced-value.h"
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/stats/test/bivariate-collector-test-suite.cc	Tue Jul 29 15:56:48 2014 -0400
@@ -0,0 +1,87 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2014 Bucknell University
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ * Author: Vinícius Daly Felizardo (vdf001@bucknell.edu)
+ *         Li Li (ll024@bucknell.edu)
+ */
+
+#include <math.h>
+
+#include "ns3/test.h"
+#include "ns3/bivariate-collector.h"
+
+using namespace ns3;
+
+const double TOLERANCE = 1e-6;
+
+// ===========================================================================
+// A simple test case
+// ===========================================================================
+
+class BivariateCollectorTestCase1 : public TestCase
+{
+public:
+  BivariateCollectorTestCase1 ();
+  virtual ~BivariateCollectorTestCase1 ();
+
+private:
+  virtual void DoRun (void);
+};
+
+BivariateCollectorTestCase1::BivariateCollectorTestCase1 ()
+  : TestCase ("Simple test case for BivariateCollector")
+
+{
+}
+
+BivariateCollectorTestCase1::~BivariateCollectorTestCase1 ()
+{
+}
+
+void
+BivariateCollectorTestCase1::DoRun()
+{
+  BivariateCollector bivariate;
+  double uVector[] = {23.0, 92.0, 7.0, 43.0, 21.0};
+  double vVector[] = {99.0, 97.0, 72.0, 6.0, 66.0};
+  int i;
+  for (i=0; i<5; i++) {
+    bivariate.Update(uVector[i], vVector[i]);
+  }
+  NS_TEST_ASSERT_MSG_EQ_TOL (bivariate.GetCorrelation(),    0.1401918,    TOLERANCE, "Correlation wrong");
+  NS_TEST_ASSERT_MSG_EQ_TOL (bivariate.GetCovariance(),    175.25,    TOLERANCE, "Covariance wrong");
+
+}
+
+// ===========================================================================
+// Test suite for BivariateCollector class
+// ===========================================================================
+
+
+class BivariateCollectorTestSuite : public TestSuite
+{
+public:
+  BivariateCollectorTestSuite ();
+};
+
+BivariateCollectorTestSuite::BivariateCollectorTestSuite ()
+  : TestSuite ("bivariate-collector", UNIT)
+{
+  AddTestCase (new BivariateCollectorTestCase1, TestCase::QUICK);
+}
+
+static BivariateCollectorTestSuite bivariateCollectorTestSuite;
--- a/src/stats/wscript	Thu Jul 24 18:05:49 2014 -0400
+++ b/src/stats/wscript	Tue Jul 29 15:56:48 2014 -0400
@@ -34,11 +34,12 @@
         'model/get-wildcard-matches.cc',
         'model/basic-stats-collector.cc',
         'model/collector.cc',
-	'model/time-driven-collector.cc',
-	'model/sum-collector.cc',
-	'model/batching-collector.cc',
-	'model/double-time-driven-collector.cc',
-	'model/double-event-driven-collector.cc',
+        'model/time-driven-collector.cc',
+        'model/sum-collector.cc',
+        'model/batching-collector.cc',
+        'model/double-time-driven-collector.cc',
+        'model/double-event-driven-collector.cc',
+        'model/bivariate-collector.cc',
         ]
 
     module_test = bld.create_ns3_module_test_library('stats')
@@ -46,11 +47,12 @@
         'test/basic-data-calculators-test-suite.cc',
         'test/average-test-suite.cc',
         'test/double-probe-test-suite.cc',
-	'test/basic-stats-collector-test-suite.cc',
-	'test/sum-collector-test-suite.cc',
-	'test/batching-collector-test-suite.cc',
-	'test/double-event-driven-collector-test-suite.cc',
-	'test/double-time-driven-collector-test-suite.cc',
+        'test/basic-stats-collector-test-suite.cc',
+        'test/sum-collector-test-suite.cc',
+        'test/batching-collector-test-suite.cc',
+        'test/double-event-driven-collector-test-suite.cc',
+        'test/double-time-driven-collector-test-suite.cc',
+        'test/bivariate-collector-test-suite.cc',
         ]
 
     headers = bld(features='ns3header')
@@ -79,11 +81,12 @@
         'model/get-wildcard-matches.h',
         'model/basic-stats-collector.h',
         'model/collector.h',
-	'model/time-driven-collector.h',
-	'model/sum-collector.h',
-	'model/batching-collector.h',
-	'model/double-time-driven-collector.h',
-	'model/double-event-driven-collector.h',
+        'model/time-driven-collector.h',
+        'model/sum-collector.h',
+        'model/batching-collector.h',
+        'model/double-time-driven-collector.h',
+        'model/double-event-driven-collector.h',
+        'model/bivariate-collector.h',
         ]
 
     if bld.env['SQLITE_STATS']: