diff --git a/code/espurna/filters/MedianFilter.h b/code/espurna/filters/MedianFilter.h index 507b4fe9..57a0b0a6 100644 --- a/code/espurna/filters/MedianFilter.h +++ b/code/espurna/filters/MedianFilter.h @@ -23,7 +23,7 @@ public: } double value() const override { - double sum { 0.0 }; + double out { 0.0 }; if (_values.size() > 2) { auto median = [](double previous, double current, double next) { @@ -44,16 +44,21 @@ public: return current; }; - for (auto prev = _values.begin(); prev != (_values.end() - 2); ++prev) { - sum += median(*prev, *std::next(prev, 1), *std::next(prev, 2)); + double counter = 0.0; + for (auto it = _values.begin(); it != (_values.end() - 2); ++it) { + out += median(*it, *std::next(it, 1), *std::next(it, 2)); + counter += 1.0; } - sum /= (_values.size() - 2); - } else if (_values.size() > 0) { - sum = _values.front(); + out /= counter; + } else if (_values.size() == 2) { + out = _values[0] + _values[1]; + out /= 2.0; + } else if (_values.size() == 1) { + out = _values.front(); } - return sum; + return out; } size_t capacity() const override { diff --git a/code/test/unit/src/filters/filters.cpp b/code/test/unit/src/filters/filters.cpp index 82b77116..2ac6fded 100644 --- a/code/test/unit/src/filters/filters.cpp +++ b/code/test/unit/src/filters/filters.cpp @@ -80,17 +80,39 @@ void test_median() { auto filter = MedianFilter(); TEST_ASSERT_EQUAL(0, filter.capacity()); - const double samples[] {1., 2., 2., 3., 4., 7., 9.}; - filter.resize(std::size(samples)); + const double one[] {4., 3., 5., 6., 2., 2., 3., 4., 7., 9.}; + filter.resize(std::size(one)); TEST_ASSERT_EQUAL(std::size(samples), filter.capacity()); TEST_ASSERT_EQUAL_DOUBLE(0.0, filter.value()); - for (const auto& sample : samples) { + for (const auto& sample : one) { + filter.update(sample); + } + + TEST_ASSERT_EQUAL_DOUBLE(4.0, filter.value()); + + const double two[] {6., 6.1, 6.2, 6.3, 6.4, 6.5, 2.5, 4.5, 2.6, 2.5, 2.4}; + filter.resize(std::size(two)); + + TEST_ASSERT_EQUAL_DOUBLE(9, filter.value()); + + for (const auto& sample : two) { + filter.update(sample); + } + + TEST_ASSERT_EQUAL_DOUBLE(4.97, filter.value()); + + const double three[] {2.4, 2.4}; + filter.resize(std::size(three)); + + TEST_ASSERT_EQUAL_DOUBLE(2.4, filter.value()); + + for (const auto& sample : three) { filter.update(sample); } - TEST_ASSERT_EQUAL_DOUBLE(3.6, filter.value()); + TEST_ASSERT_EQUAL_DOUBLE(2.4, filter.value()); } void test_moving_average() {