「FIRディジタルフィルタの作成」でPython言語によるFIRディジタルフィルタの作成を作成しました。今回は、C#言語を使って、FIRディジタルフィルタを作成します。入力・出力ともwavファイルとします。
開発/実行環境
- Visual Studio2013 Express (C#)
- Windows 7 Professional
FIRディジタルフィルタソフトの作成
C#言語を使ってFIRディジタルフィルタスクリプトを作成します。「wavファイルの作成とwavファイル情報の表示」で作成したwavファイルを入力します。ただし、記録時間は30秒から3秒にしました。
- 32行目のSystem.IO.StreamReaderメソッドでフィルタ係数ファイル「constant」を読み込み、38行目でフィルタ係数を保存します。
- 48行目でFile.ReadAllBytesメソッドを使ってwavファイルをバイナリで読み込みます。
- 49行目のfor文で、「0x2c」バイト分オフセットをかけて、wavファイルのヘッダ部分をスキップします。wavファイルのヘッダ部分の構成については「C#によるWaveファイルの解析」を参照してください。
- FIRディジタルフィルタの処理にはQueue クラスを使用します。タップ数分キューに挿入しておき、64行目でそれぞれの入力データに対してフィルタ係数を乗算していきます。
- 67行目は、キューに挿入されているデータがタップ数に満たない場合の判断を行っています。
- 58行目の「32768.0」や73行目の「10000.0」は正規化もどきの為に使用しています。処理結果を見ながら増減させてください。
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.IO;
namespace FirFilter
{
class Program
{
static void Main(string[] args)
{
string line;
string coeffFile = "constant";
string wavFile = "100-500-1000-8000hz.wav";
string wavFileOut = "100-500-1000-8000hzOut.wav";
const int taps = 10;
double[] coefficients = new double[taps];
Queue<double> buffer = new Queue<double>();
int i = 0;
double output = 0;
double input = 0;
byte[] data;
byte[] sounddata = new byte[4];
int posoffset = 0x2c;
StreamReader file = new System.IO.StreamReader(coeffFile);
for (i = 0; i < taps; i++)
{
if ((line = file.ReadLine()) != null)
{
coefficients[i] = double.Parse(line);
}
else
{
Console.WriteLine("Could not read the coefficients from {0}", coeffFile);
}
}
file.Close();
data = File.ReadAllBytes(wavFile);
for (i = posoffset; i < data.Length; i += 2)
{
if (buffer.Count == taps)
{
buffer.Dequeue();
}
input = (short)((data[i + 1] << 8) + data[i + 0]);
buffer.Enqueue(input/32768.0);
int k = buffer.Count - 1;
// i = 0;
output = 0;
foreach (double value in buffer)
{
output += coefficients[k] * value;
// Console.WriteLine("coefficients:{0} value:{1} ", coefficients[k], value);
k--;
if (k < 0)
{
break;
}
}
// Console.WriteLine("****pixcel: {0} {1} /{2} ",i, input, output);
output *= 10000.0;
sounddata = BitConverter.GetBytes((int)output);
data[i + 0] = sounddata[0];
data[i + 1] = sounddata[1];
}
File.WriteAllBytes(wavFileOut, data);
}
}
}
System.IO.StreamReaderメソッドで読み込まれるファイル「constant」の内容を次に示します。この係数により高周波成分が減衰し、波形も滑らかになります。
0.1 0.1 0.1 0.1 0.1 0.1 0.1 0.1 0.1 0.1
FIRディジタルフィルタソフトの実行
入力したwavファイル「100-500-1000-8000hz.wav」を次に示します。
FIRディジタルフィルタ後のwavファイル「100-500-1000-8000hzOut.wav」を次に示します。高周波成分が減衰したため高い音が小さくなり、低音が拡大されています。
audacityアプリを用いて、今回のC#言語によるFIRディジタルフィルタ後の波形「100-500-1000-8000hzOut.wav」(上側)と前回のPython言語によるFIRディジタルフィルタ後の波形「fir.wav」(下側)を比較します。
audacityアプリでFIRディジタルフィルタ後の波形をFFT処理すると、100、500、1000、8000hzのそれぞれが変わっていないことが確認できました。

