Pytorch Argrelmax function (or C++)
I'm trying to find the equivalent pytorch (or C++) for scipy.signal.argrelmax(), which finds the peaks in a 1D array with some padding. https://docs.scipy.org/doc/scipy-0.14.0/reference/generated/scipy.signal.argrelmax.html

Here's what I've come up with and it is faster than scipy.signal.argrelmax - but I'm missing a fast solution to the last step which deletes peaks within some window.

import torch

# initalize an array (not the one in plot below)
gpu_max = torch.rand(100000)

# find peaks and troughs by subtracting shifted versions
gpu_temp1 = gpu_max[1:-1]-gpu_max[:-2]
gpu_temp2 = gpu_max[1:-1]-gpu_max[2:]

# and checking where both shifts are positive;
out1 = torch.where(gpu_temp1&gt;0, gpu_temp1*0+1, gpu_temp1*0)
out2 = torch.where(gpu_temp2&gt;0, out1, gpu_temp2*0)

# argrelmax containing all peaks
argrelmax_gpu = torch.nonzero(out2, out=None)+1


So the top plot which marks every single relmaxpeak is pretty fast. But need the bottom one - which comes from scipy.signal.argrelmax() and uses a 30sample time window (i.e. it only returns maxima within a 60 time point window).

EDIT: I've updated code to reflect updated torch.nonzero() search.  But still need to figure out how to do the last step (in figure below).


Ok, so someone on pytorch forums did have a pretty good solution: https://discuss.pytorch.org/t/pytorch-argrelmax-or-c-function/36404

Here's the full answer in case it gets deleted:

    a = #1D Array of  your choice
    window_maxima = torch.nn.functional.max_pool1d_with_indices(a.view(1,1,-1), width, 1, padding=width//2)[1].squeeze()
    candidates = window_maxima.unique()
    nice_peaks = candidates[(window_maxima[candidates]==candidates).nonzero()]

