おおよそ70〜80kのサイズのバイト配列を取得し、それらを時間領域から周波数領域に変換したいと思います(おそらくDFTを使用)。私はwikiをフォローしており、これまでのところこのコードを取得しています。
for (int k = 0; k < windows.length; k++) {
double imag = 0.0;
double real = 0.0;
for (int n = 0; n < data.length; n++) {
double val = (data[n])
* Math.exp(-2.0 * Math.PI * n * k / data.length)
/ 128;
imag += Math.cos(val);
real += Math.sin(val);
}
windows[k] = Math.sqrt(imag * imag + real
* real);
}
私の知る限り、それは各周波数ウィンドウ/ビンの大きさを見つけます。次に、窓を通り抜けて、マグニチュードが最大のものを見つけます。信号を再構築するときに使用するために、その周波数にフラグを追加します。再構成された信号が元のデータ セットと一致するかどうかを確認します。次に高い周波数のウィンドウが見つからない場合は、信号を再構築するときに使用するフラグを立てます。
これは、信号を再構築するためのコードです。これは、非常に間違っていると確信しています (IDFT を実行することになっています)。
for (int n = 0; n < data.length; n++) {
double imag = 0.0;
double real = 0.0;
sinValue[n] = 0;
for (int k = 0; k < freqUsed.length; k++) {
if (freqUsed[k]) {
double val = (windows[k] * Math.exp(2.0 * Math.PI * n
* k / data.length));
imag += Math.cos(val);
real += Math.sin(val);
}
}
sinValue[n] = imag* imag + real * real;
sinValue[n] /= data.length;
newData[n] = (byte) (127 * sinValue[n]);
}
freqUsed は、信号を再構成するときに周波数ウィンドウを使用する必要があるかどうかをマークするために使用されるブール配列です。
とにかく、発生する問題は次のとおりです。
- すべての周波数ウィンドウが使用されても、信号は再構成されません。これは、...
- Math.exp() の値が大きすぎて、無限大が返されることがあります。これにより、正確な計算を取得することが難しくなります。
- ガイドとして wiki に従っていますが、私のデータが意味があるかどうかを判断するのは困難です。これにより、問題のテストと特定が困難になります。
問題から離れて:
私はこれにかなり慣れていないので、すべてを完全には理解していません。したがって、任意のヘルプまたは洞察をいただければ幸いです。時間を割いてすべてをお読みいただき、ありがとうございます。また、ご提供いただけるご支援に感謝いたします。私がこれを可能な限り最悪の方法で行っていると思われるとしても、どんな助けも本当に良いです. 再度、感謝します。
-
編集:
そこで、コードを次のように更新しました。
for (int k = 0; k < windows.length; k++) {
double imag = 0.0;
double real = 0.0;
for (int n = 0; n < data.length; n++) {
double val = (-2.0 * Math.PI * n * k / data.length);
imag += data[n]*-Math.sin(val);
real += data[n]*Math.cos(val);
}
windows[k] = Math.sqrt(imag * imag + real
* real);
}
元の変換と :
for (int n = 0; n < data.length; n++) {
double imag = 0.0;
double real = 0.0;
sinValue[n] = 0;
for (int k = 0; k < freqUsed.length; k++) {
if (freqUsed[k]) {
double val = (2.0 * Math.PI * n
* k / data.length);
imag += windows[k]*-Math.sin(val);
real += windows[k]*Math.cos(val);
}
}
sinValue[n] = Math.sqrt(imag* imag + real * real);
sinValue[n] /= data.length;
newData[n] = (byte) (Math.floor(sinValue[n]));
}
逆変換用。私はまだそれが正しく機能していないことを心配していますが。単一の正弦波を保持する配列を生成しましたが、それを分解/再構築することさえできません。私が欠けているものについての洞察はありますか?