AJA NTV2 SDK  17.5.0.1242
NTV2 SDK 17.5.0.1242
performance.cpp
Go to the documentation of this file.
1 /* SPDX-License-Identifier: MIT */
8 // Includes
12 #include "ajabase/system/debug.h"
13 
14 #include <iomanip>
15 #include <sstream>
16 #include <math.h>
17 
18 using std::string;
19 using std::map;
20 
22 // Definitions
24 
25 // Fix for old Linux systems
26 #ifndef UINT64_MAX
27 #define UINT64_MAX 18446744073709551615
28 #endif
29 
30 AJAPerformance::AJAPerformance(const std::string& name,
31  AJATimerPrecision precision,
32  uint64_t skipEntries)
33  : mTimer(precision)
34 {
35  mName = name;
36  mTotalTime = 0;
37  mEntries = 0;
38  mMinTime = UINT64_MAX;
39  mMaxTime = 0;
40  mMean = 0.0;
41  mM2 = 0.0;
42  mNumEntriesToSkipAtStart = skipEntries;
43 }
44 
45 AJAPerformance::AJAPerformance(const std::string& name,
46  const AJAPerformanceExtraMap &values,
47  AJATimerPrecision precision,
48  uint64_t skipEntries)
49  : mTimer(precision)
50 {
51  mName = name;
52  mTotalTime = 0;
53  mEntries = 0;
54  mMinTime = UINT64_MAX;
55  mMaxTime = 0;
56  mExtras = values;
57  mMean = 0.0;
58  mM2 = 0.0;
59  mNumEntriesToSkipAtStart = skipEntries;
60 }
61 
63  uint64_t skipEntries)
64  : mTimer(precision)
65 {
66  mName = "";
67  mTotalTime = 0;
68  mEntries = 0;
69  mMinTime = UINT64_MAX;
70  mMaxTime = 0;
71  mMean = 0.0;
72  mM2 = 0.0;
73  mNumEntriesToSkipAtStart = skipEntries;
74 }
75 
77 {
78  // If not already stopped then stop and output report
79  if (mTimer.IsRunning())
80  {
81  Stop();
82  Report();
83  }
84 }
85 
87 {
88  mExtras = values;
89 }
90 
91 std::string AJAPerformance::Name(void)
92 {
93  return mName;
94 }
95 
97 {
98  return mEntries;
99 }
100 
102 {
103  return mTotalTime;
104 }
105 
107 {
108  return mMinTime;
109 }
110 
112 {
113  return mMaxTime;
114 }
115 
117 {
118  return mMean;
119 }
120 
122 {
123  uint64_t entries = Entries();
124  if (entries > 1)
125  {
126  return mM2/(entries-1);
127  }
128  else
129  return 0.0;
130 }
131 
133 {
134  return sqrt(Variance());
135 }
136 
138 {
139  return mExtras;
140 }
141 
143 {
144  return mTimer.Precision();
145 }
146 
148 {
149  mTimer.Start();
150 }
151 
153 {
154  uint32_t elapsedTime;
155 
156  mTimer.Stop();
157  elapsedTime = mTimer.ElapsedTime();
158 
159  // Honor the number of entries asked to skip at start
160  if (mNumEntriesToSkipAtStart > 0)
161  {
162  mNumEntriesToSkipAtStart--;
163  return;
164  }
165 
166  mTotalTime += elapsedTime;
167  mEntries++;
168 
169  // calculate the running mean and sum of squares of differences from the current mean (mM2)
170  // mM2 is needed to calculate the variance and the standard deviation
171  // see: https://stackoverflow.com/a/17053010
172  // http://en.wikipedia.org/wiki/Algorithms_for_calculating_variance#Online_algorithm
173  double delta1 = elapsedTime - mMean;
174  mMean += delta1/mEntries;
175  double delta2 = elapsedTime - mMean;
176  mM2 += delta1 * delta2;
177 
178  if (elapsedTime > mMaxTime)
179  {
180  mMaxTime = elapsedTime;
181 
182  // First-time assignment in the event that a
183  // test run has times that always monotonically
184  // increase.
185  if (elapsedTime < mMinTime)
186  {
187  mMinTime = elapsedTime;
188  }
189  }
190  else if (elapsedTime < mMinTime)
191  {
192  mMinTime = elapsedTime;
193  }
194 }
195 
196 void AJAPerformance::Report(const std::string& name, const char* pFileName, int32_t lineNumber)
197 {
198  int entries = (int)Entries();
199  if (entries > 0)
200  {
201  int min = (int)MinTime();
202  int max = (int)MaxTime();
203  double mean = Mean();
204  double stdev = StandardDeviation();
205  string times = (entries == 1) ? "time, " : "times, ";
206  string reportName = name.empty() ? Name() : name;
207 
208  std::ostringstream oss;
209  oss << " [" << std::left << std::setw(23) << std::setfill(' ') << reportName << "] " <<
210  "called " << std::right << std::setw(4) << entries << " " << times <<
211  "min: " << std::right << std::setw(4) << min << ", " <<
212  "mean: " << std::right << std::setw(5) << std::fixed << std::setprecision(2) << mean << ", " <<
213  "stdev: " << std::right << std::setw(5) << std::fixed << std::setprecision(2) << stdev << ", " <<
214  "max: " << std::right << std::setw(4) << max;
215 
218  pFileName == NULL ? __FILE__ : pFileName,
219  lineNumber < 0 ? __LINE__ : lineNumber,
220  oss.str());
221  }
222 }
223 
225  std::string key, AJATimerPrecision precision, uint64_t skipEntries)
226 {
227  if(stats.find(key) == stats.end())
228  {
229  // not already in map
230  AJAPerformance newStatsGroup(key, precision, skipEntries);
231  stats[key] = newStatsGroup;
232  }
233 
234  AJAPerformanceTracking::iterator foundAt = stats.find(key);
235  if(foundAt != stats.end())
236  {
237  foundAt->second.Start();
238  return true;
239  }
240  else
241  {
242  return false;
243  }
244 }
245 
247  std::string key, const AJAPerformanceExtraMap& extras, AJATimerPrecision precision,
248  uint64_t skipEntries)
249 {
250  if(stats.find(key) == stats.end())
251  {
252  // not already in map
253  AJAPerformance newStatsGroup(key, extras, precision, skipEntries);
254  stats[key] = newStatsGroup;
255  }
256 
257  AJAPerformanceTracking::iterator foundAt = stats.find(key);
258  if(foundAt != stats.end())
259  {
260  foundAt->second.Start();
261  return true;
262  }
263  else
264  {
265  return false;
266  }
267 }
268 
270 {
271  AJAPerformanceTracking::iterator foundAt = stats.find(key);
272  if(foundAt != stats.end())
273  {
274  foundAt->second.Stop();
275  return true;
276  }
277  else
278  {
279  return false;
280  }
281 }
282 
283 bool AJAPerformanceTracking_report(AJAPerformanceTracking& stats, std::string title, const char *pFileName, int32_t lineNumber)
284 {
285  const int32_t unit = (int32_t)AJA_DebugUnit_StatsGeneric;
286  const int32_t severity = (int32_t)AJA_DebugSeverity_Debug;
287 
288  if (stats.size() > 0)
289  {
290  if (title.empty())
291  {
292  title = "stats_report";
293  }
294 
295  string units = AJATimer::PrecisionName(stats.begin()->second.Precision(), true);
296 
297  std::ostringstream title_oss;
298  std::ostringstream units_oss;
299  std::ostringstream footer_oss;
300  title_oss << title << ", tracking " << stats.size() << " {";
301  units_oss << " * time units are in " << units << " *";
302  footer_oss << "}";
303 
304  AJADebug::Report(unit, severity, pFileName, lineNumber, title_oss.str());
305  AJADebug::Report(unit, severity, pFileName, lineNumber, units_oss.str());
306 
307  AJAPerformanceTracking::iterator foundAt = stats.begin();
308  while (foundAt != stats.end())
309  {
310  std::string key = foundAt->first;
311  AJAPerformance perf = foundAt->second;
312 
313  perf.Report(key, pFileName, lineNumber);
314 
315  ++foundAt;
316  }
317 
318  AJADebug::Report(unit, severity, pFileName, lineNumber, footer_oss.str());
319  return true;
320  }
321  else
322  {
323  return false;
324  }
325 }
AJAPerformance::MinTime
uint64_t MinTime(void)
Definition: performance.cpp:106
AJATimer::IsRunning
bool IsRunning(void) const
Definition: timer.h:81
AJAPerformance::Variance
double Variance(void)
Definition: performance.cpp:121
AJA_DebugUnit_StatsGeneric
@ AJA_DebugUnit_StatsGeneric
Definition: debugshare.h:56
AJAPerformance
Definition: performance.h:23
performance.h
Declaration of the AJAPerformance class.
AJAPerformance::AJAPerformance
AJAPerformance(const std::string &name, AJATimerPrecision precision=AJATimerPrecisionMilliseconds, uint64_t skipEntries=0)
Definition: performance.cpp:30
NULL
#define NULL
Definition: ntv2caption608types.h:19
AJATimerPrecision
AJATimerPrecision
Definition: timer.h:14
AJAPerformance::Mean
double Mean(void)
Definition: performance.cpp:116
AJADebug::Report
static void Report(int32_t index, int32_t severity, const char *pFileName, int32_t lineNumber,...)
Definition: debug.cpp:389
AJAPerformance::Extras
const AJAPerformanceExtraMap Extras(void)
Definition: performance.cpp:137
AJAPerformanceExtraMap
std::map< std::string, uint64_t > AJAPerformanceExtraMap
Definition: performance.h:18
AJAPerformance::MaxTime
uint64_t MaxTime(void)
Definition: performance.cpp:111
AJAPerformance::Precision
AJATimerPrecision Precision(void)
Definition: performance.cpp:142
AJAPerformanceTracking_report
bool AJAPerformanceTracking_report(AJAPerformanceTracking &stats, std::string title, const char *pFileName, int32_t lineNumber)
Definition: performance.cpp:283
AJAPerformance::Report
void Report(const std::string &name="", const char *pFileName=NULL, int32_t lineNumber=-1)
Definition: performance.cpp:196
AJA_DebugSeverity_Debug
@ AJA_DebugSeverity_Debug
Definition: debugshare.h:32
AJAPerformanceTracking_start
bool AJAPerformanceTracking_start(AJAPerformanceTracking &stats, std::string key, AJATimerPrecision precision, uint64_t skipEntries)
Definition: performance.cpp:224
AJATimer::Stop
void Stop(void)
Definition: timer.cpp:36
UINT64_MAX
#define UINT64_MAX
Definition: performance.cpp:27
AJAPerformanceTracking
std::map< std::string, AJAPerformance > AJAPerformanceTracking
Definition: performance.h:154
AJAPerformanceTracking_stop
bool AJAPerformanceTracking_stop(AJAPerformanceTracking &stats, std::string key)
Definition: performance.cpp:269
AJATimer::PrecisionName
static std::string PrecisionName(const AJATimerPrecision precision, const bool longName=true)
Definition: timer.cpp:111
AJAPerformance::Entries
uint64_t Entries(void)
Definition: performance.cpp:96
AJAPerformance::SetExtras
void SetExtras(const AJAPerformanceExtraMap &values)
Definition: performance.cpp:86
AJATimer::ElapsedTime
uint32_t ElapsedTime(void) const
Definition: timer.cpp:58
AJAPerformance::TotalTime
uint64_t TotalTime(void)
Definition: performance.cpp:101
AJAPerformance::~AJAPerformance
~AJAPerformance(void)
Definition: performance.cpp:76
AJAPerformance::StandardDeviation
double StandardDeviation(void)
Definition: performance.cpp:132
AJAPerformance::Start
void Start(void)
Definition: performance.cpp:147
AJATimer::Precision
AJATimerPrecision Precision(void) const
Definition: timer.h:88
AJATimer::Start
void Start(void)
Definition: timer.cpp:22
AJAPerformance::Name
std::string Name(void)
Definition: performance.cpp:91
debug.h
Declares the AJADebug class.
AJAPerformance::Stop
void Stop(void)
Definition: performance.cpp:152