Go to the documentation of this file.00001 #ifndef MOVING_MEDIAN_H
00002 #define MOVING_MEDIAN_H
00003
00015 #include <deque>
00016 #include <algorithm>
00017
00018
00019 namespace qrk
00020 {
00026 template<class T> class MovingMedian
00027 {
00028 public:
00035 MovingMedian(size_t size, T initial_value = 0)
00036 : buffer_size_(size), median_index_(size >> 1)
00037 {
00038 if (buffer_size_ == 0) {
00039 buffer_size_ = 1;
00040 }
00041 buffer_set(buffer_size_, initial_value);
00042 }
00043
00044
00050 void setMedianValue(T value)
00051 {
00052 buffer_set(buffer_size_, value);
00053 }
00054
00055
00061 T median(void)
00062 {
00063 return median_;
00064 }
00065
00066
00074 T push_back(T value)
00075 {
00076 buffer_.pop_front();
00077 buffer_.push_back(value);
00078
00079
00080
00081 std::deque<T> copied = buffer_;
00082 std::nth_element(copied.begin(),
00083 copied.begin() + median_index_, copied.end());
00084 median_ = copied[median_index_];
00085
00086 return median_;
00087 }
00088
00089 private:
00090 MovingMedian(const MovingMedian& rhs);
00091 MovingMedian& operator = (const MovingMedian& rhs);
00092
00093 std::deque<T> buffer_;
00094 size_t buffer_size_;
00095 T median_;
00096 int median_index_;
00097
00098
00099 void buffer_set(size_t size, T& value)
00100 {
00101 buffer_.clear();
00102 buffer_.assign(size, value);
00103 median_ = value;
00104 }
00105 };
00106 }
00107
00108 #endif