ubicomplab / rPPG-Toolbox

rPPG-Toolbox: Deep Remote PPG Toolbox (NeurIPS 2023)
https://arxiv.org/abs/2210.00716
Other
504 stars 129 forks source link

How to estimate the SNR of a ppg signal when there is no true value? #291

Closed 408550969 closed 4 months ago

408550969 commented 4 months ago

In actual testing, there is no true value ppg signal. How to estimate the SNR or similar indicators of a video stream so as to determine whether the heart rate value of this video stream is displayed

girishvn commented 4 months ago

Hi,

I would suggest writing code for a comb filter. This calculates the energy under the first and second harmonic. You can compare this against the energy under the rest of the frequency spectrum. This value should be proportional to SNR.

This requires taking the frequency spectrum of the predicted signal, and finding the lowest frequency peak for which there is a peak at the second harmonic.

This method is often times crude, and unless the prediction exhibits strong periodicity may not perform very well.

Hope this helps.

408550969 commented 4 months ago

Based on your description, am I writing it correctly like this:

def _calculate_fft_hr(ppg_signal, fs, low_pass, high_pass,truth):
    ppg_signal = np.expand_dims(ppg_signal, 0)
    N = 2048
    f_ppg, pxx_ppg = scipy.signal.periodogram(ppg_signal, fs=fs, nfft=N, detrend=False)
    fmask_ppg = np.argwhere((f_ppg >= low_pass) & (f_ppg <= high_pass))
    mask_ppg = np.take(f_ppg, fmask_ppg)
    mask_pxx = np.take(pxx_ppg, fmask_ppg)
    fft_hr = np.take(mask_ppg, np.argmax(mask_pxx, 0))[0] * 60

    signal_energy = np.sum(mask_pxx)
    f1 = np.argmax(mask_pxx)   
    f2 = 2 * f1               
    if(f2< len(mask_pxx)):
        comb_filter_SNR = (mask_pxx[f1] + mask_pxx[f2]) / (signal_energy - mask_pxx[f1] - mask_pxx[f2])
    else:
        comb_filter_SNR = (mask_pxx[f1]) / (signal_energy - mask_pxx[f1])
    print("comb_filter_SNR = ",comb_filter_SNR)
jungyin commented 2 months ago

_calculate_fft_hr

Can you calculate SNR normally using this method? The rppg generated during my use is used to generate HR Very unstable, may I ask if you are stable?