Python实现15采样点延迟 绘制希尔伯特变换时域幅值图求助
Remez希尔伯特变换Matlab转Python修正方案
原代码核心错误点
- 滤波器设计参数不匹配:
scipy.signal.remez的频段、期望增益参数需要成对匹配,原代码错误将通带范围减半,且增益长度和频段不匹配,无法生成和Matlab一致的30阶希尔伯特变换FIR系数。 - 滤波函数选型错误:Matlab的
filter是单遍因果滤波,原代码使用的filtfilt是零相位双向滤波,不会产生FIR滤波器固有的群延迟,和原Matlab逻辑完全不符,需替换为scipy.signal.lfilter。 - 15采样点延迟实现错误:原代码直接用列表拼接两个数组,得到的是嵌套列表而非一维数值数组,且索引对齐错误。Matlab的延迟逻辑为序列前补15个0,截断原信号最后15个点接在零值后,需用numpy数组拼接方法实现。
- 时间序列长度不匹配:原代码生成的时间序列比Matlab版本少1个采样点,会导致索引对齐偏差。
修正后完整代码
import numpy as np from scipy import signal as sig import matplotlib.pyplot as plt # 设计30阶希尔伯特变换FIR滤波器,完全匹配Matlab remez参数 filter_order = 30 coeff_len = filter_order + 1 pass_band = [0.05, 0.95] # 归一化通带,1对应奈奎斯特频率,和Matlab定义一致 pass_gain = [1, 1] b = sig.remez(coeff_len, bands=pass_band, desired=pass_gain, type='hilbert') # 生成测试信号 fs = 1000 duration = 2 t = np.arange(0, duration + 1/fs, 1/fs) # 0~2s共2001个点,和Matlab t向量长度一致 x = np.sin(2 * np.pi * 50 * t) # 因果滤波得到希尔伯特变换结果 xh = sig.lfilter(b, 1, x) # 实现15采样点延迟 delay_sample = 15 xd = np.concatenate([np.zeros(delay_sample), x[:-delay_sample]]) # 绘制前50个采样点的时域曲线 plt.plot(t[:50], xd[:50], label='延迟15点输入信号') plt.plot(t[:50], xh[:50], label='希尔伯特变换输出') plt.xlabel('时间 [s]') plt.ylabel('幅值') plt.grid(True) plt.legend() plt.show()
效果说明
30阶线性相位FIR滤波器的固定群延迟为阶数/2 = 15个采样点,将原信号延迟15个点后,即可和滤波输出的希尔伯特变换信号相位对齐,得到和Matlab完全一致的90度相移时域曲线。
内容的提问来源于stack exchange,提问作者Jonah
相关产品推荐
相关产品推荐

