最近导师要求我将师兄写的一篇关于fsk调制解调的MATLAB代码用VS2013编成C语言,方便后续应用到工程实践中。由于本人编程水平有限,并且C语言只有在大学的时候水水的学过一遍,所以此次代码可能有许多疏漏,欢迎批评指正。
1.明确目标
本次要用C语言实现如下代码功能:
recv_lowfilter = fir1(256,1.2*2*Br/fs);
这是一句MATLAB代码,该句代码的重点在于 fir1 这个函数。
2.明确功能
fir1 这个函数是MATLAB中的自带函数,但是C语言中却没有该功能函数,因此,要首先弄清楚该函数实现的功能。所以,我去查找了MATLAB的官网。
此处为该函数的连接:https://ww2.mathworks.cn/help/signal/ref/fir1.html
fir1 是根据窗函数法设计的有限长滤波器。本次我们只实现第一个句法,即只输入两个参数n和Wn,来实现一个滤波器。
我们可以来看一下参数列表:
输入参数:n 是滤波器的阶数,Wn是滤波器的截止频率。
输出参数:b是滤波器的参数,长度是n+1。
功能总结:就是输入滤波器的阶数和截止频率,fir1函数会返回一个长度为n+1的向量,该向量的组成为滤波器的系数(B(z) = b(1) + b(2)z + … + b(n+1)z–n.)。
3.原理及实现流程
原理:
理想滤波器的冲击响应是非因果的、无限长的,窗函数法是从时域出发,用因果的、有限长的冲击响应去逼近非因果的无限长的理想滤波器。窗函数的作用相当于截取其中的一段。
其中hd(n)是理想的无限长的非因果的滤波器,w(n)是窗函数,h(n)是我们用窗函数逼近的滤波器,即我们所求。
fir1函数中,默认使用hamming窗,该窗的计算公式为:
流程:
4.代码
#include <stdio.h>
#include <math.h>
#include<vector>
#define PI 3.1415926f
using namespace std;
vector <double> fir1(int N, double w) //N=256,hamming,N为阶数256,滤波器长度是N+1=257
{
int a = N / 2; //这里的N是阶数,是长度-1
vector <int> n;
int i0;
for (i0 = 0; i0 <= N; i0++)
{
n.push_back(i0);
}
int len_n = n.size();
int i1;
vector <double> m;
for (i1 = 0; i1 < len_n; i1++)
{
double eps = 2.2204e-16;
m.push_back(n[i1] - a + eps);
}
int len_m = m.size();
vector <double> h;//ideal理想滤波器
int i2;
for (i2 = 0; i2 < len_m; i2++)
{
h.push_back(sin(w * m[i2]) / (PI * m[i2]));
}
vector <double> B;//hamming窗系数
int i3;
for (i3 = 0; i3 < N; i3++)
{
B.push_back(0.54 - 0.46*cos(2.0 * PI * i3 / (N - 1)));
}
//hd = h.* B
vector <double> hd;
int i4;
for (i4 = 0; i4 < N; i4++)
{
hd.push_back( h[i4] * B[i4]);
}
return hd;
}