发新帖本帖赏金 5.00元(功能说明)我要提问
返回列表
打印

请问如何进行FFT滤波

[复制链接]
楼主: a3724395
手机看帖
扫描二维码
随时随地手机跟帖
41
奥本海默的教材吃透你就懂了
一点一点看别人写的简易资料对于没有基础的人来说没有什么意义

使用特权

评论回复
42
一周一天班| | 2017-9-9 09:28 | 只看该作者
FFT是一个周期(一段时间)内的分析,不能用于实时的滤波。两码事情。

使用特权

评论回复
43
nethopper| | 2017-9-9 13:13 | 只看该作者
雪山飞狐D 发表于 2017-9-9 01:43
你可以看下一些应用,比如90度截止频率为500HZ,而信号刚好有一个会频移频率尖峰,495HZ-505HZ不定期移动, ...

你说的情况应该是由于时域截短后有频谱泄漏造成的,在一个有频谱泄漏的频谱上做FFT滤波就不能达到理想状态,会产生一些artifact。频谱泄漏很多时候无法避免,但只要采集时间足够长,泄漏就会小,对滤波后的信号影响会局限在信号段的前后两端很小的范围内。由于FFT滤波后所剩下的各频率分量的实部和虚部没有变化,所以相位没变。

在没有频谱泄漏的特殊情况下,FFT滤波是相当精准的、理想的,即使是信号位于滤波器的截止频率附近。下面给个例子:

原信号由1000.488281 Hz 1Vpp +  1001.953125 Hz 1Vpp构成,两者的初始相位都从零开始,采样频率48000Hz, 32768个采样点,即:对1000.488281H采集了683个整周期,对1001.953125H采集了684个整周期,没有频谱泄漏,也就是将采集的信号在时域做周期延拓后跟原来的信号完全一致。因此频谱为两个孤立的谱线。由于两个频率非常接近,时域波形图还显示出了明显的“啪”..频。如下图所示。


然后再选择FFT低通滤波(brick-wall型),截止频率设置为1001,由下图可见,滤波后剩下了干干静静、准准确确的1000.488281 Hz 1Vpp,且其初始相位未变。


当然为了实现某种时域特性或效果,减小泄漏的影响,在频域做FFT滤波时也可以不采用简单的直上直下,而采用渐变的频域特性...

使用特权

评论回复
44
mycomputer0000| | 2017-9-9 13:27 | 只看该作者
a3724395 发表于 2017-9-8 19:23
请问这位朋友,什么情况下需要关心相位
我认为常见的情况是一定频率的波形,经过AD采集后变成数字量,然 ...

返回时域后在整体上看相位当然是和原来不一样了,因为丢掉了一部分频率,但保留下来的频率其相位振幅是没有变的,上面那位说的相位全乱了应该是说保留下来的频率合成为一个时域信号后相位和以前不一样了

使用特权

评论回复
45
雪山飞狐D| | 2017-9-9 20:19 | 只看该作者
本帖最后由 雪山飞狐D 于 2017-9-9 20:38 编辑
nethopper 发表于 2017-9-9 13:13
你说的情况应该是由于时域截短后有频谱泄漏造成的,在一个有频谱泄漏的频谱上做FFT滤波就不能达到理想状 ...

截止频率的陡降性能与相位的保持是一个矛盾体,越是陡降性能越好的滤波器,其相位变化越剧烈,尤其是在截止频率附近,即使是FIR线性相位,在截止频率附近的相位也是变化比较大,更不用说这种90度的截止,更类似于无穷阶数椭圆滤波器,你这种纯手工的操作造成的相位保持,只能推导你的验证步骤存在某些逻辑误区,或者是纯粹我想多了

使用特权

评论回复
46
nethopper| | 2017-9-10 22:01 | 只看该作者
雪山飞狐D 发表于 2017-9-9 20:19
截止频率的陡降性能与相位的保持是一个矛盾体,越是陡降性能越好的滤波器,其相位变化越剧烈,尤其是在截 ...

前面43楼的确是个比较理想的例子,理想的条件是整周期采样,无频谱泄漏。话也说回来,工程上采用整周期采样来避免频谱泄漏的例子不少。

下面给个普通的有频谱泄漏的例子来看看采用直上直下的FFT滤波的利弊。原信号由100Hz 1Vpp 方波 + 550Hz 1Vpp 正弦波构成,两者的初始相位都从零开始,采样频率48000Hz, 采样时间1秒, 这个不是整周期采样,从频谱图上可以看出频谱不为孤立的谱线,有明显的频谱泄漏现象,如下图所示。采用方波的原因主要是其频带非常宽,滤波后容易看出是否有相位失真。



然后再选择FFT带阻滤波(brick-wall型),截止频率设置为525Hz~575Hz,以滤除550Hz的正弦波,只留下100Hz 1Vpp的方波。由于采样点数为48000,不是FFT采用的2^N, 软件内部做FFT滤波时自动会选择65536点FFT, 也就是说尾部自动补了65536-48000=17536个零,这个对平滑周期延拓的不连续可能有好处。结果如下图所示。从图可见,这种FFT滤波的Artifact主要出现在波形的前端和后端(因为周期延拓不连续),而中间的绝大部分数据受到的影响很小,关键是它显示了滤波后方波的形状,幅度和初始相位都基本没变。


上图显示的是经FFT滤波后波形的全貌,下图是特写。



在实际应用中,有时侯可用掐头去尾的方法,只取中段来获取经FFT滤波后的波形的时域特性,比如可获取波形的峰峰值等。



使用特权

评论回复
47
nethopper| | 2017-9-10 22:15 | 只看该作者
雪山飞狐D 发表于 2017-9-9 20:19
截止频率的陡降性能与相位的保持是一个矛盾体,越是陡降性能越好的滤波器,其相位变化越剧烈,尤其是在截 ...

“即使是FIR线性相位,在截止频率附近的相位也是变化比较大”-----不是线性相位吗?你说的是常见的带阻区的180度跳变?

使用特权

评论回复
48
雪山飞狐D| | 2017-9-11 01:52 | 只看该作者
本帖最后由 雪山飞狐D 于 2017-9-11 02:52 编辑
nethopper 发表于 2017-9-10 22:15
“即使是FIR线性相位,在截止频率附近的相位也是变化比较大”-----不是线性相位吗?你说的是常见的带阻区 ...

FIR 线性相位并不是说相位不变而是跟频率成正比,是一个线性,反应到群延迟这个参数是一个常量,可以看到其实保持线性相位的频率截断第一个阶跃反弹点其实很浅,最后一个图是椭圆滤波器的相位,它的幅频响应就非常类似与直接大角度截断,可以看出相位的剧烈变化,你手动仿真的跟理论上的区别在哪里,我也不知道,或者你把那个大角度的低通截断(非带阻),作为一个幅频响应做反傅里叶变换,然后在时域里信号做卷积,也许效果应该是跟把信号做FFT然后在频域里面低通截断一样的,这样也许就会表现出椭圆滤波器类似的各种突变相位,不知道逻辑或者理论偏差在哪里

QQ图片20170911013549.png (304.93 KB )

QQ图片20170911013549.png

QQ图片20170911020946.png (83 KB )

QQ图片20170911020946.png

QQ图片20170911015156.png (205.15 KB )

QQ图片20170911015156.png

使用特权

评论回复
49
nethopper| | 2017-9-11 23:58 | 只看该作者
雪山飞狐D 发表于 2017-9-11 01:52
FIR 线性相位并不是说相位不变而是跟频率成正比,是一个线性,反应到群延迟这个参数是一个常量,可以看到 ...

"...可以看到其实保持线性相位的频率截断第一个阶跃反弹点其实很浅..."??????--------这是由于你贴的图分辨率不够,产生误导了。而且对数坐标无法反应幅度过零甚至为负(如果可以允许的话)的情况。实际上,幅频响应在最低点应该是零而非“很浅”。而那些相位跳变与这些幅频响应的零点是一致的,而且如果你仔细看的话会发现跳变是180度,这正是我前面提到的。如果允许幅度为负的话(就是画幅频响应时对幅度不取绝对值),那么线性相位的FIR的相频特性就是一条直线到底了。。

滤波器首先要区分:因果(Causal), 非因果(Non-Causal), 反因果(Anti-Causal)三种。线性相位需要冲激响应对称或反对称,因而必须是非因果的,所以椭圆滤波器肯定无法实现线性相位了。至于这里的FFT滤波器,当然是非因果的,不仅是线性相位,而且是零相位(zero-phase)的。

使用特权

评论回复
50
nethopper| | 2017-9-14 18:28 | 只看该作者
本帖最后由 nethopper 于 2017-9-14 19:47 编辑

前面说了只要滤波器的冲激响应对称就能得到线性相位,下面用实例看看FFT滤波器,FIR滤波器和IIR滤波器的冲激响应有什么不同。实例是1秒长的采样频率为48kHz的数据,数据除了正中间0.5秒处的采样点的数值为1外,其余的采样点的数值皆为零。就是说0.5秒处存在一个单位冲激。如果让这个单位冲激通过数字滤波器,在时域(示波器窗口)就得到该滤波器的单位冲激响应,在 频 域 ( 频 谱 分 析 仪 窗 口 )就得到该滤波器的频率响应。

1. 单位冲激(未滤波前)
时域:单位冲激
频域:一条水平直线



2. 单位冲激经过6kHz的FFT低通滤波后得到该滤波器的冲激响应及频响
时域:滤波器的冲激响应以t=0.5秒对称,因此是线性相位,而且中心位于0.5秒处,因此没有延迟。而在单位冲激到来之前(t=0.5秒前),竟然就有输出了,所以是非因果的。非因果滤波器是通过延迟来HOLD住那些“将来的输入点”。

频域:频响陡直但有明显过冲(如果对时域的冲激响应做谱分析前不加窗的话,也就是施加矩形窗的话)


3. 单位冲激经过6kHz的1022阶(即:1023个点)FIR低通滤波后得到该滤波器的冲激响应及频响
时域:滤波器的冲激响应以t=0.5106秒对称,因此是线性相位,而且中心位于0.5106秒处,因此延迟了0.0106秒,可如此计算:(1023-1)/2/48000=0.0106 秒。这个延迟在后处理时是可补偿的。由于此FIR滤波器的每个输出点都对称地用到了过去的一半和将来的一半输入点(包括当前点),因此是非因果的。非因果滤波器是通过延迟来HOLD住那些“将来的输入点”。

频域:作为FIR滤波器设计的常用方法之一,实际上这个FIR滤波的设计本身就是将理想的低通滤器陡直的幅频响应反变换到时域得到冲激响应,然后加窗(图中为Kaiser 6窗)以减缓幅频响应由于时域截短带来的过冲。只要在时域截短时采用对称截取,就能实现线性相位。



4. 单位冲激经过6kHz的12阶巴特饿死IIR低通滤波后得到该滤波器的冲激响应及频响
时域:滤波器的冲激响应是非对称的,因此无法实现线性相位。由于输出点完全由过去的输入点和当前的输入点决定,因此是因果的。
频域:说点啥呢。




使用特权

评论回复
51
nethopper| | 2017-9-18 23:22 | 只看该作者
本帖最后由 nethopper 于 2017-9-18 23:27 编辑

在上楼的例子中,FFT低通滤波和FIR低通滤波的冲激响应基本上是一个形状,截短了的未加窗和加窗的SINC函数。
FIR滤波是在时域做滤波,用滤波器的冲激响应在时域做卷积;
FFT滤波是在频域做滤波,用滤波器的频率响应在频域做乘法,再反变换回时域。
既然频域乘积就等于时域卷积,那么两者是否完全等效?区别是FIR滤波做的是线性卷积而FFT滤波从时域来看做的是循环卷积。

如果对时间序列补足够多的零,可在效果上将循环卷积转变为线性卷积。在时域做长序列快速线性卷积时,常用的Overlap-Add法和Overlap-Save法就是先将长序列分段,然后技巧性地将FFT的循环卷积变为线性卷积并利用FFT速度快的特点来加速的。

那么IIR就不能实现线性相位了吗?答案是传统的有模拟原型的那种因果的IIR不行,非因果的IIR则可能,只要冲激响应对称就行,常见例子是Forward-Backward filter,就是把冲激响应正向来卷积一遍,然后反过来从负向来卷积一遍,相移正负相抵,实现零相位,当然这只适用于对数据进行后处理。

总之,对于FFT滤波,你很可能以为在对如下信号做滤波(整周期采样,无频谱泄漏,周期延拓边界连续):



而实际上你很可能是在对如下信号做滤波(非整周期采样,频谱泄漏,周期延拓边界不连续):


对上面这个边界不连续、有断点的地方,怎么滤都会有边界效应的。

使用特权

评论回复
52
nethopper| | 2017-9-22 12:44 | 只看该作者
有的时候并不希望将某些频率分量衰减到0,而是希望将它们进行一定程度的衰减,比如衰减XX分贝,这时只需将FFT后的该频率分量的实部和虚部同时按比例衰减即能保证相位不变。

FFT滤波方便之处在于可以任意设定滤波器的幅频响应并保持相位不变,下面是用FFT实现任意幅频响应的C程序,

void FFTArbitrayFiltering(double * xr, double * xi, long FFTSize, double * Gain)
{
long i,k;
k=FFTSize/2;
Nto2NFFT(xr,xi,FFTSize,0);
xr[0]*=pow(10.0,Gain[0]/20);
xi[0]*=pow(10.0,Gain[0]/20);
for(i=1;i<k;i++)
{
  xr[i]*=pow(10.0,Gain[i]/20);xr[FFTSize-i]*=pow(10.0,Gain[i]/20);
  xi[i]*=pow(10.0,Gain[i]/20);xi[FFTSize-i]*=pow(10.0,Gain[i]/20);
}
xr[k]*=pow(10.0,Gain[k]/20);
xi[k]*=pow(10.0,Gain[k]/20);
FFT(xr,xi,FFTSize,1);
}

使用特权

评论回复
53
a3724395|  楼主 | 2017-9-22 17:16 | 只看该作者
nethopper 发表于 2017-9-22 12:44
有的时候并不希望将某些频率分量衰减到0,而是希望将它们进行一定程度的衰减,比如衰减XX分贝,这时只需将F ...

这个程序是FFT滤波程序还是干什么用的?原理有点看不明白

使用特权

评论回复
54
nethopper| | 2017-9-24 22:09 | 只看该作者
a3724395 发表于 2017-9-22 17:16
这个程序是FFT滤波程序还是干什么用的?原理有点看不明白

FFTArbitrayFiltering  //FFT任意幅频响应滤波程序
(
double * xr,  //输入/输出数据的实部
double * xi,  //输入/输出数据的虚部,输入时应设置为零
long FFTSize, //FFT的点数
double * Gain //滤波器的幅频响应(用分贝表示)
)



Nto2NFFT   //将N点的实序列FFT用N/2点的普通FFT来计算,以进一步加快计算速度
(
xr,         //输入/输出数据的实部
xi,         //输入/输出数据的虚部,输入时应设置为零
FFTSize,    //FFT的点数
0           //FFT(正变换)
)


FFT        //普通的FFT
(
xr,         //输入/输出数据的实部
xi,         //输入/输出数据的虚部
FFTSize,    //FFT的点数
1           //iFFT(反变换)
)

使用特权

评论回复
55
a3724395|  楼主 | 2017-9-26 22:18 | 只看该作者
nethopper 发表于 2017-9-24 22:09
FFTArbitrayFiltering  //FFT任意幅频响应滤波程序
(
double * xr,  //输入/输出数据的实部

nethopper,很佩服你理论知识的强大,但提下质疑,不知以下我做的是否正确:
下图是我输入10HZ,幅值2V的正弦波(上面的波形),间隔5ms采样,采样时间1s,FFT后没有置零任何频率,直接IFFT,然后也以5ms间隔DA输出(下面的波形)
1,从这两个波形看,是不是相位已经发生了变化?
2,谁能解释下突然出现的脉冲是怎么回事?因为是仿真的,没接硬件应该不会出现干扰。
C:\Documents and Settings\Administrator\桌面

使用特权

评论回复
56
a3724395|  楼主 | 2017-9-26 22:23 | 只看该作者
如图

QQ截图20170926215924.png (119.95 KB )

QQ截图20170926215924.png

使用特权

评论回复
57
nethopper| | 2017-9-27 13:02 | 只看该作者
a3724395 发表于 2017-9-26 22:18
nethopper,很佩服你理论知识的强大,但提下质疑,不知以下我做的是否正确:
下图是我输入10HZ,幅值2V的 ...

单一频率是看不出相位失真的。

FFT滤波很难实现连续不间断地运行,每个FFT段边界处很可能是不连续的,不清楚具体你选的FFT段的长度。如果要实时滤波,应采用FIR或IIR,在时域做。除此之外,你这个DAC输出明显还需要做低通滤波。

使用特权

评论回复
58
kingkits| | 2017-9-28 11:20 | 只看该作者
关键是FFT / IFFT 主要时用于调制/解调 数字信号用的,滤波还是老老实实的用FIR/IIR 比较好,最主要的原因是计算量(或者说是时间)。

使用特权

评论回复
59
nethopper| | 2017-9-30 12:21 | 只看该作者
本帖最后由 nethopper 于 2017-9-30 12:29 编辑
nethopper 发表于 2017-9-22 12:44
有的时候并不希望将某些频率分量衰减到0,而是希望将它们进行一定程度的衰减,比如衰减XX分贝,这时只需将F ...

FFT滤波需要找准FFT结果中的各点所对应的中心频率,这个貌似简单,但却容易出错。下图显示了FFT结果中的各点所对应的中心频率,以N=16点FFT为例。实序列的FFT结果是共轭对称的,即:F [ i ] = F [ N-i ]*, i=0~N-1。然而魔鬼总是藏在细节中(the devil is in the details),i=0和i=N/2就找不到共轭怼家了,仔细研究会发现这两个点的虚部总为零。这就补充解释了第52楼程序为啥要把FFT后的第一点和第N/2点做单独处理。不过第N/2点的结果不必太当真,这个点已经是位于Nyquist频率上了。   




使用特权

评论回复
60
gujiamao12345| | 2017-10-1 11:55 | 只看该作者
根据fft出来的结果调节rc频点,但是速度不一定跟得上

使用特权

评论回复
发新帖 本帖赏金 5.00元(功能说明)我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则