基于Python的NeuroKit2库从ECG信号提取呼吸频率(BPM)求助
从ECG信号提取呼吸频率(BPM)的NeuroKit2实现问题
我尝试用NeuroKit2库从ECG信号中提取以呼吸次数/分钟(BPM)为单位的呼吸频率(RR),参考了ECG衍生呼吸(EDR)相关文档但对用法理解模糊,网上也没找到可参考的实际实现代码,自己写了一段代码但不确定是否正确,希望得到技术支持。
我编写的代码
import neurokit2 as nk import numpy as np ecg = nk.data('ecg_1000hz.csv') sampling_rate = 1000 # 可视化信号 nk.signal_plot(ecg) # 测试ecg_rsp()函数的所有可用方法 method_name_lst = ["vangent2019", "sarkar2015", "charlton2016", "soni2019"] # 清洗ECG信号以去除噪声,提高峰值检测精度 cleaned_ecg = nk.ecg_clean(ecg_signal=ecg, sampling_rate=sampling_rate, method="neurokit") # 使用指定方法在ECG信号中查找R波峰值 rpeaks, info = nk.ecg_peaks(cleaned_ecg, sampling_rate=sampling_rate) # 根据峰值序列计算信号速率(每分钟) ecg_rate = nk.signal_rate(rpeaks, sampling_rate=sampling_rate, desired_length=len(rpeaks)) for method_name in method_name_lst: print("Method: {}\n".format(method_name)) # 提取ECG衍生呼吸(EDR) resp_signal = nk.ecg_rsp(ecg_rate, sampling_rate=sampling_rate, method=method_name) # 清洗呼吸信号 rsp_cleaned = nk.rsp_clean(resp_signal, sampling_rate=sampling_rate) # 计算呼吸频率 rsp_rate_onsets = nk.rsp_rate(rsp_cleaned, sampling_rate=sampling_rate, method="trough") rsp_rate_xcorr = nk.rsp_rate(rsp_cleaned, sampling_rate=sampling_rate, method="xcorr") print("\tMean RR (Trough): {}\n".format(np.mean(rsp_rate_onsets))) print("\tMean RR (Xcorr): {}\n".format(np.mean(rsp_rate_xcorr)))
代码中的关键问题
ecg_rsp输入错误:nk.ecg_rsp()的正确输入是原始/清洗后的ECG信号,而非你传入的ecg_rate(心率序列)。多数EDR方法直接从ECG波形提取呼吸调制信号,不需要先计算心率。- 信号长度不匹配:
nk.signal_rate()返回的ecg_rate长度远短于原始ECG信号,会导致后续衍生呼吸信号长度异常,影响频率计算准确性。 - EDR信号清洗冗余:
nk.rsp_clean()是为真实呼吸信号设计的,部分EDR方法输出的信号已处理过,额外清洗可能引入误差。
修正后的实现代码
import neurokit2 as nk import numpy as np # 加载数据 ecg = nk.data('ecg_1000hz.csv') sampling_rate = 1000 # 1. 预处理ECG信号 cleaned_ecg = nk.ecg_clean(ecg, sampling_rate=sampling_rate) # 2. 提取R波峰值(部分EDR方法需用到该信息) rpeaks, _ = nk.ecg_peaks(cleaned_ecg, sampling_rate=sampling_rate) # 测试所有EDR方法 method_list = ["vangent2019", "sarkar2015", "charlton2016", "soni2019"] for method in method_list: print(f"=== 使用方法: {method} ===") # 3. 提取EDR信号:直接传入清洗后的ECG,部分方法自动调用R峰数据 edr_signal, info = nk.ecg_rsp(cleaned_ecg, sampling_rate=sampling_rate, method=method, rpeaks=rpeaks) # 4. 计算呼吸频率 rsp_rate_trough = nk.rsp_rate(edr_signal, sampling_rate=sampling_rate, method="trough") rsp_rate_xcorr = nk.rsp_rate(edr_signal, sampling_rate=sampling_rate, method="xcorr") # 输出平均呼吸频率(用nanmean排除异常值) print(f"平均呼吸频率(波谷法): {np.nanmean(rsp_rate_trough):.2f} BPM") print(f"平均呼吸频率(互相关法): {np.nanmean(rsp_rate_xcorr):.2f} BPM\n") # 可选:可视化EDR信号与原始ECG对比 nk.signal_plot([cleaned_ecg, edr_signal], labels=["清洗后ECG", "EDR信号"], sampling_rate=sampling_rate)
关键说明
- EDR方法逻辑:不同EDR方法实现逻辑不同,部分方法(如
vangent2019)需要R峰辅助,nk.ecg_rsp()会自动处理,无需手动传入心率序列。 - 频率计算注意:
nk.rsp_rate()返回瞬时呼吸频率序列,用np.nanmean()计算平均值可排除异常值干扰。 - 结果验证:若有同步真实呼吸信号,可对比EDR提取结果,选择最适配数据的EDR方法。
内容的提问来源于stack exchange,提问作者Nikolaos Sintoris
相关产品推荐
相关产品推荐

