43 SST_ELI_DECLARE_STATISTIC_TEMPLATE_DERIVED(
48 SST_ELI_ELEMENT_VERSION(1, 0, 0),
49 "Track distribution of statistic across bins",
52 SST_ELI_DOCUMENT_PARAMS(
53 {
"minvalue",
"The minimum data value to include in the histogram.",
"0"},
54 {
"binwidth",
"The size of each histogram bin.",
"5000"},
55 {
"numbins",
"The number of histogram bins.",
"100"},
56 {
"dumpbinsonoutput",
"Whether to output the data range of each bin as well as its value.",
"true"},
57 {
"includeoutofbounds",
"Whether to keep track of data that falls below or above the histogram bins in separate out-of-bounds bins.",
"true"})
61 BaseComponent* comp,
const std::string& statName,
const std::string& statSubId,
Params& statParams) :
65 std::vector<std::string> allowedKeySet;
66 allowedKeySet.push_back(
"minvalue");
67 allowedKeySet.push_back(
"binwidth");
68 allowedKeySet.push_back(
"numbins");
69 allowedKeySet.push_back(
"dumpbinsonoutput");
70 allowedKeySet.push_back(
"includeoutofbounds");
74 m_minValue = statParams.
find<BinDataType>(
"minvalue", 0);
75 m_binWidth = statParams.
find<NumBinsType>(
"binwidth", 5000);
76 m_numBins = statParams.
find<NumBinsType>(
"numbins", 100);
77 m_dumpBinsOnOutput = statParams.
find<
bool>(
"dumpbinsonoutput",
true);
78 m_includeOutOfBounds = statParams.
find<
bool>(
"includeoutofbounds",
true);
85 m_itemsBinnedCount = 0;
95 virtual const std::string&
getStatTypeName()
const override {
return stat_type_; }
103 SST_SER(m_OOBMinCount);
104 SST_SER(m_OOBMaxCount);
105 SST_SER(m_itemsBinnedCount);
106 SST_SER(m_totalSummed);
107 SST_SER(m_totalSummedSqr);
109 SST_SER(m_dumpBinsOnOutput);
110 SST_SER(m_includeOutOfBounds);
119 void addData_impl_Ntimes(uint64_t N, BinDataType value)
override
122 if ( value < getBinsMinValue() ) {
126 if ( value > getBinsMaxValue() ) {
133 m_totalSummed += N * value;
134 m_totalSummedSqr += N * (value * value);
137 m_itemsBinnedCount++;
143 double calc1 = (double)value / (
double)m_binWidth;
144 double calc2 = floor(calc1);
145 double calc3 = m_binWidth * calc2;
146 BinDataType bin_start = (BinDataType)calc3;
150 HistoMapItr_t bin_itr = m_binsMap.find(bin_start);
153 if ( bin_itr == m_binsMap.end() ) {
155 m_binsMap.insert(std::pair<BinDataType, CountType>(bin_start, (CountType)N));
159 bin_itr->second += N;
163 void addData_impl(BinDataType value)
override { addData_impl_Ntimes(1, value); }
167 NumBinsType getActiveBinCount() {
return m_binsMap.size(); }
170 NumBinsType getNumBins() {
return m_numBins; }
173 NumBinsType getBinWidth() {
return m_binWidth; }
179 CountType getBinCountByBinStart(BinDataType binStartValue)
182 HistoMapItr_t bin_itr = m_binsMap.find(binStartValue);
185 if ( bin_itr == m_binsMap.end() ) {
191 return m_binsMap[binStartValue];
199 BinDataType getBinsMinValue() {
return m_minValue; }
205 BinDataType getBinsMaxValue()
208 return (m_binWidth * m_numBins) + m_minValue - 1;
215 uint64_t getStatCollectionCount()
225 CountType getItemsBinnedCount()
228 return m_itemsBinnedCount;
235 BinDataType getValuesSummed() {
return m_totalSummed; }
241 BinDataType getValuesSquaredSummed() {
return m_totalSummedSqr; }
246 m_totalSummedSqr = 0;
249 m_itemsBinnedCount = 0;
257 m_Fields.push_back(statOutput->
registerField<BinDataType>(
"BinsMinValue"));
258 m_Fields.push_back(statOutput->
registerField<BinDataType>(
"BinsMaxValue"));
259 m_Fields.push_back(statOutput->
registerField<NumBinsType>(
"BinWidth"));
260 m_Fields.push_back(statOutput->
registerField<NumBinsType>(
"TotalNumBins"));
261 m_Fields.push_back(statOutput->
registerField<BinDataType>(
"Sum"));
262 m_Fields.push_back(statOutput->
registerField<BinDataType>(
"SumSQ"));
263 m_Fields.push_back(statOutput->
registerField<NumBinsType>(
"NumActiveBins"));
264 m_Fields.push_back(statOutput->
registerField<CountType>(
"NumItemsCollected"));
265 m_Fields.push_back(statOutput->
registerField<CountType>(
"NumItemsBinned"));
267 if (
true == m_includeOutOfBounds ) {
268 m_Fields.push_back(statOutput->
registerField<CountType>(
"NumOutOfBounds-MinValue"));
269 m_Fields.push_back(statOutput->
registerField<CountType>(
"NumOutOfBounds-MaxValue"));
273 if (
true == m_dumpBinsOnOutput ) {
277 for ( uint32_t y = 0; y < getNumBins(); y++ ) {
279 binLL = (y * (uint64_t)getBinWidth()) + getBinsMinValue();
280 binUL = binLL + getBinWidth() - 1;
282 std::stringstream ss;
283 ss <<
"Bin" << y <<
":" << binLL <<
"-" << binUL;
284 m_Fields.push_back(statOutput->
registerField<CountType>(ss.str().c_str()));
291 StatisticOutput::fieldHandle_t x = 0;
292 statOutput->
outputField(m_Fields[x++], getBinsMinValue());
293 statOutput->
outputField(m_Fields[x++], getBinsMaxValue());
294 statOutput->
outputField(m_Fields[x++], getBinWidth());
295 statOutput->
outputField(m_Fields[x++], getNumBins());
296 statOutput->
outputField(m_Fields[x++], getValuesSummed());
297 statOutput->
outputField(m_Fields[x++], getValuesSquaredSummed());
298 statOutput->
outputField(m_Fields[x++], getActiveBinCount());
299 statOutput->
outputField(m_Fields[x++], getStatCollectionCount());
300 statOutput->
outputField(m_Fields[x++], getItemsBinnedCount());
302 if (
true == m_includeOutOfBounds ) {
303 statOutput->
outputField(m_Fields[x++], m_OOBMinCount);
304 statOutput->
outputField(m_Fields[x++], m_OOBMaxCount);
308 if (
true == m_dumpBinsOnOutput ) {
309 BinDataType currentBinValue = getBinsMinValue();
310 for ( uint32_t y = 0; y < getNumBins(); y++ ) {
311 statOutput->
outputField(m_Fields[x++], getBinCountByBinStart(currentBinValue));
313 currentBinValue += getBinWidth();
320 using HistoMap_t = std::map<BinDataType, CountType>;
323 using HistoMapItr_t =
typename HistoMap_t::iterator;
326 BinDataType m_minValue;
329 NumBinsType m_binWidth;
332 NumBinsType m_numBins;
335 CountType m_OOBMinCount;
336 CountType m_OOBMaxCount;
340 CountType m_itemsBinnedCount;
344 BinDataType m_totalSummed;
348 BinDataType m_totalSummedSqr;
351 HistoMap_t m_binsMap;
354 std::vector<StatisticOutput::fieldHandle_t> m_Fields;
355 bool m_dumpBinsOnOutput;
356 bool m_includeOutOfBounds;
358 inline static const std::string stat_type_ =
"Histogram";