在安卓开发的时候有时间要对音频,振动等信号进行滤波,下面是一段音频信号经过高通滤波后和低通滤波后的效果
可以看到滤波效果是只过滤出需要频率的信号,将噪音去掉
下面是java代码
public class Filter { private static double rate = 0.000000001; private static Double[] audha = {1.0, -1.98388104166084, 0.984009917549517}; private static Double[] audhb = {0.991972739802589, -1.98394547960518, 0.991972739802589}; private static Double[] audla = {1.0,-7.12374475999005,22.2456381652698,-39.7699187284106,44.5164561572107,-31.9455283104170,14.3513710384153,-3.68998752786006,0.415714445797744}; private static Double[] audlb = {1.87506157822703*rate,1.50004926258163*rate*10,5.25017241903569*rate*10, 1.05003448380714*rate*100,1.31254310475892*rate*100,1.05003448380714*rate*100,5.25017241903569*rate*10, 1.50004926258163*rate*10,1.87506157822703*rate}; private static Double[] in; private static Double[] out; private static Double[] outData; public static Double[] highpass(Double[] signal) { return filter(signal, audha, audhb); } public static Double[] lowpass(Double[] signal) { return filter(signal, audla, audlb); } private static Double[] filter(Double[] signal, Double[] a, Double[] b) { in = new Double[b.length]; out = new Double[a.length - 1]; outData = new Double[signal.length]; for (int i = 0; i < signal.length; i++) { System.arraycopy(in, 0, in, 1, in.length - 1); //in[1]=in[0],in[2]=in[1]... in[0] = signal[i]; //calculate y based on a and b coefficients //and in and out. Double y = 0.0; for (int j = 0; j < b.length; j++) { if (in[j] != null) { y += b[j] * in[j]; } } for (int j = 0; j < a.length - 1; j++) { if (out[j] != null) { y -= a[j + 1] * out[j]; } } //shift the out array System.arraycopy(out, 0, out, 1, out.length - 1); out[0] = y; outData[i] = y; } return outData; } }
这里的audha,audhb,audla,audlb四个参数是怎么来的呢
我是从matlab代码得来的,看一下matlab的高低通滤波
function [dataOut,a,b]=lowpass(data,fs,f) %低通滤波:滤除 f HZ以上的信号 [b,a] = butter(8,f/fs*2); dataOut = filter(b,a,data);
function [dataOut,a,b]=highpass(data,fs,f) %高通滤波 [b,a] = butter(2,f/fs*2,'high'); dataOut = filter(b,a,data);
使用,就会得到高通的参数a,b和低通的参数a,b。这里我使用的是11025HZ的频率,过滤掉20HZ以下的
[traindata,a,b]=highpass(traindata,11025,20);
就得到a,b
低通滤波同理,把得到的四个参数复制到java代码里面即可。
java代码调用传入数组即可得到滤波后的数组