Mercurial > hg > qm-dsp
changeset 407:f898c901c055
Fix handling of NaNs in MedianFilter, & test for it
author | Chris Cannam <c.cannam@qmul.ac.uk> |
---|---|
date | Mon, 23 Feb 2015 10:42:54 +0000 |
parents | ebde9a50bb74 |
children | 5316fa4b0f33 |
files | maths/MedianFilter.h tests/TestMedianFilter.cpp |
diffstat | 2 files changed, 49 insertions(+), 2 deletions(-) [+] |
line wrap: on
line diff
--- a/maths/MedianFilter.h Tue Aug 05 17:12:46 2014 +0100 +++ b/maths/MedianFilter.h Mon Feb 23 10:42:54 2015 +0000 @@ -48,8 +48,9 @@ void push(T value) { if (value != value) { - std::cerr << "WARNING: MedianFilter::push: attempt to push NaN" << std::endl; - return; // nan + std::cerr << "WARNING: MedianFilter::push: attempt to push NaN, pushing zero instead" << std::endl; + // we do need to push something, to maintain the filter length + value = T(); } drop(m_frame[0]); const int sz1 = m_size-1;
--- a/tests/TestMedianFilter.cpp Tue Aug 05 17:12:46 2014 +0100 +++ b/tests/TestMedianFilter.cpp Mon Feb 23 10:42:54 2015 +0000 @@ -3,6 +3,7 @@ #include "maths/MedianFilter.h" #include <cmath> +#include <cstdlib> #define BOOST_TEST_DYN_LINK #define BOOST_TEST_MAIN @@ -171,6 +172,51 @@ BOOST_CHECK_EQUAL(ifilt.get(), 2); } +BOOST_AUTO_TEST_CASE(inf) +{ + // Inf and -Inf should behave normally + double pinf = strtod("Inf", 0); + double ninf = strtod("-Inf", 0); + MedianFilter<double> dfilt(3); + dfilt.push(1.0); + dfilt.push(2.0); + dfilt.push(pinf); + BOOST_CHECK_EQUAL(dfilt.get(), 2.0); + dfilt.push(pinf); + BOOST_CHECK_EQUAL(dfilt.get(), pinf); + dfilt.push(pinf); + BOOST_CHECK_EQUAL(dfilt.get(), pinf); + dfilt.push(2.0); + BOOST_CHECK_EQUAL(dfilt.get(), pinf); + dfilt.push(1.0); + BOOST_CHECK_EQUAL(dfilt.get(), 2.0); + dfilt.push(ninf); + BOOST_CHECK_EQUAL(dfilt.get(), 1.0); + dfilt.push(pinf); + BOOST_CHECK_EQUAL(dfilt.get(), 1.0); + dfilt.push(ninf); + BOOST_CHECK_EQUAL(dfilt.get(), ninf); +} + +BOOST_AUTO_TEST_CASE(nan) +{ + // The filter should never accept a NaN, because it breaks sorting + // and comparison and that will break the filter. Instead it + // should insert 0. + double nan = strtod("NaN", 0); + MedianFilter<double> dfilt(3); + dfilt.push(1.0); + dfilt.push(2.0); + dfilt.push(nan); + BOOST_CHECK_EQUAL(dfilt.get(), 1.0); + dfilt.push(nan); + BOOST_CHECK_EQUAL(dfilt.get(), 0.0); + dfilt.push(-11.0); + BOOST_CHECK_EQUAL(dfilt.get(), 0.0); + dfilt.push(-1.0); + BOOST_CHECK_EQUAL(dfilt.get(), -1.0); +} + BOOST_AUTO_TEST_SUITE_END()