#pragma once #include #include namespace dnnlowp { /** * bin_width = (max - min)/nbins * ith bin (zero-based indexing) contains [i*bin_width, (i+1)*bin_width) * with an exception that (nbins - 1)th bin contains * [(nbins-1)*bin_width, nbins*bin_width] * * Make sure to call Finalize before GetHistogram to reduce per-thread * histogram. */ class Histogram { public: Histogram(int nbins, float min, float max) : min_(min), max_(max), histogram_(nbins) {} Histogram(float min, float max, const std::vector& bins) : min_(min), max_(max), histogram_(bins) {} void Add(float f, uint64_t cnt = 1); /** * This version collects histogram with multiple threads using per-thread * histogram with privatization. * We should call Finalize before GetHistogram to reduce per-thread * histogram. */ void Add(const float* f, int len); float Min() const { return min_; } float Max() const { return max_; } /** * Reduce per-thread histogram. Need to call this before GetHistogram when * the version of Add with multiple threads was used. */ void Finalize(); const std::vector* GetHistogram() const { return &histogram_; } private: float min_, max_; std::vector histogram_; std::vector per_thread_histogram_; }; /// An equi-width histogram where the spread of bins change over time when /// we see new min or max values. class DynamicHistogram { public: DynamicHistogram(int nbins); void Add(float f); void Add(const float* f, int len); /// Indicate we're not dynamically adjusting histogram bins any more and /// return the current static histogram. const Histogram* Finalize(); private: /// Dynamic histogram is implemented by the series of static histograms /// histograms_[i+1] is a new histogram "expanded" from histograms_[i] when /// we see a new extremum. /// An invariant: the beginning of the first bin of histograms_[i] exactly /// matches with the beginning of a bin in histograms_[i+1]. The end of the /// last bin of histograms_[i] exactly matches with the end of a bin in /// histograms_[i+1]. std::vector histograms_; int nbins_; float min_, max_; std::unique_ptr final_histogram_; }; // class DynamicHistogram } // namespace dnnlowp