音声音響情報処理 其の二 20180417
はじめに
今回は,scilabを使って音声どうしの畳み込みまでやっていきました.理論的なことはあまり出てきませんでしたので,コードばかりのノートになると思いますが,悪しからず.
scilab操作
一応,今回の講義で使ったプログラムは以下の通り.
音の出力
t=(1:8000)/8000; //サンプリング周波数8kHz x=0.3*sin(2*%pi*1000*t); //角周波数1kHzのsin波を生成 plot(x(1:100)); //時刻100までの波形を出力 sound(x,8000); //サンプリングレート8kHzで再生
これなんですが,サンプリングレートを低くしたら低速で,高くしたら高速で再生されるようになります.
フーリエ変換
scilabには,fftという関数があります.これを使うと,離散フーリエ変換をしてくれるという仕組みになっています.ちなみに,離散フーリエ変換は以下のように記述できます.
ただし,離散フーリエ変換ではサンプル数(ここではのこと)が異なれば,1メモリが表す数が異なることにも注意したい.不確定性というらしい.
ということで,コードを書いていきましょう.
fx=fft(x); plot(20.*log10(abs(fx)));
人間の感覚は対数に対応しているので,このような式でプロット.また,単純な大きさ(絶対値)でプロットしているのは,虚数空間を無視するためです.
これでプロットされたのが次のグラフ.
さっきの「1メモリが変わる」というのもやってみましょうか.
fx=fft(x(1:4000)); plot(20.*log10(abs(fx)));
サンプル数を8000個から4000個に落とします.そうして出てきたのが次のグラフ.
どちらも,角周波数に設定した1kHzにスペクトルのピークが出ているのですが,前者は横軸が8000,後者は横軸が4000であることが分かります.サンプル数を半分に落とした分,横軸の1メモリに対応する値が2倍になったことがここからも確認できますね.
そのほか,グラフにピーク値が二つあるのはサンプリング定理によるもの.サンプリング周波数の半分(エイリアス)で折り返されるというあれですね.
音の足し合わせ
音は線形なので,足し合わすことができます.ということでコードを.
t=(1:8000)/8000; //サンプリング周波数8kHz x1=0.3*sin(2*%pi*1000*t); x2=0.3*sin(2*%pi*3000*t); x3=x1+x2; //足し合わせる sound(x3,8000); //音を聞く fx=fft(x3); //フーリエ変換 plot(20.*log10(abs(fx))); //プロット
出てきたグラフは次の通り.
きれいに1kHzと3kHzの場所にピークが来てますね.面白い.今度は,x2の方を半分にして足し合わせてみます.
x3=x1+0.5*x2; //足し合わせる sound(x3,8000); //音を聞く fx=fft(x3); //フーリエ変換 plot(20.*log10(abs(fx))); //プロット
出てきたグラフはこんな感じ.
3kHzの方だけピーク値が低いです.分かりにくいという人のために拡大画像を.
こんな感じ.音の大きさが半分になると,大体6dBだけピークが低くなることが分かっています.これは,デシベルの計算をみても理解できます.