There is an array of data of this type data array with peaks

It is necessary to find the average view of all peaks, i.e. determine the peaks in the data array, write each peak into a separate list, and then calculate the average value of each corresponding point of all peaks.

i=7800 peak=[] while i<8249: i=i+1 if massiv[i]>0.02: peak.append(float(massiv[i])) 

So far, I have only selected all elements from the initial array more than a certain number (for a start, 0.02)

then on the data table looked at the boundaries of the peaks and wrote down four of them. then calculated the average value of the corresponding points. however, the peaks have different widths, so I took only the first 7 points along the minimum width of the peak

 peak1=peak[0:12] peak2=peak[13:22] peak3=peak[23:31] peak4=peak[32:42] i=-1 peakmid=[] while i<7: i=i+1 peakmid.append((peak1[i]+peak2[i]+peak3[i]+peak4[i])/4) plt.plot(peakmid) plt.show() 

enter image description here

That's about what should work.

  • Did you try to do anything yourself? And specify what is the average view of all the peaks? Maybe you need to find the average peak amplitude? - Avernial
  • one
    Do you need to find all extremums of a one-dimensional array? - BanyRule
  • @Avernial tried to do this manually, but there are quite a lot of such graphs, so I’m looking for a software solution. The average view means the average amplitude and width of the baseShalom Alecheim
  • I mean, what program tried to do? - Avernial
  • @Avernial added what he had already done - Shalom Alecheim

1 answer 1

A thought is approximately like this: there is a threshold (let it be 0.02), as soon as the value in the array exceeds this threshold - we consider this as the beginning of the peak, remember its index. Further, while the value exceeds the threshold - the peak continues. As soon as it ceases to exceed - we consider the end of the peak, we make a cut of the array values ​​from the beginning to the end of the peak, add to the list of peaks (well, or do the generator function and return through yield ).

It will look something like this:

 def get_peaks(arr, thres): # Параметры: массив, пороговое значение peak_start = -1 # -1 будет обозначать, что пик еще не начался или уже закончился for i, value in enumerate(arr): if peak_start >= 0: if value < thres: # Возвращаем срез массива с данным пиком: yield arr[peak_start:i] peak_start = -1 # Отмечаем, что пик закончился else: if value >= thres: peak_start = i # Не забываем про пики, которые могут граничить с концом массива: if peak_start >= 0: yield arr[peak_start:] # Пример вызова: print(list(get_peaks(massiv, 0.02))) 

Next, we have a list of peaks. It is necessary to go through all the peaks in parallel, taking the average of each value at the corresponding point. For shorter peaks, fill 0 to the desired length (the fillvalue parameter in the zip_longest function).

 peaks = get_peaks(massiv, 0.02) from itertools import zip_longest mean_profile = [sum(row)/len(row) for row in zip_longest(*peaks, fillvalue=0)] 
  • Sincerely thank you! However, with the second action there was a snag. mean_profile in its original form did not work. I had to replace the zip_longest with izip_longest . However, this is not the essence of the issue. Python swears that get_peaks should be iterable. Replaced it with peaks . Does not swear anymore, however, the same peaks prints without changes - Shalom Alecheim
  • zip_longest is for Python 3, for Python 2 is the izip_longest . I fixed the code (replaced get_peaks with peaks and added an asterisk), check now. - insolor
  • Yes, it all worked now! - Shalom Alecheim