Search code examples
javamathnoise

Factoring out noise in an algorithm


I essentially have a bunch of data objects which map timestamps in milliseconds to float values. I'm looking to essentially find the peak/max of the data in a given range. I've been essentially using something like this:

float previousValue = 0;
for (int i = 0; i < data.size(); i++) {
    MyData value = data.get(i);
    if (value.getData() < previousValue) {
        // found the peak!
        break;
    } else {
        previousValue = value.getData();
    }
}

The only problem with this algorithm is that it doesn't account for noise. Essentially, I could have values like this:

[0.1025, 0.3000, 0.3025, 0.3500, 0.3475, 0.3525, 0.1025]

The actual peak is at 0.3525, but my algorithm above would see it as 0.3500, as it comes first. Due to the nature of my calculations, I can't just do max() on the array and find out the largest value, I need to find the largest value that comes first before it falls.

How can I find the top of my peak, while accounting for some variance in noise?


Solution

  • There are two issues:

    1. filtering out the noise;
    2. finding the peak.

    It seems like you already have a solution for 2, and need to solve 1.

    To filter out the noise, you need some kind of low-pass filter. A moving average is one such filter. For example, exponential moving average is very easy to implement and should work well.

    In summary: put your series through the filter, and then apply the peak finding algorithm.