10

.3gpp オーディオ ファイルに対して高速フーリエ変換を実行しようとしています。このファイルには、電話のマイクからの 44100kHz での 5 秒間の短い録音が含まれています。

私が見つけることができるすべてのJava FFTアルゴリズムは、明らかな理由から、double []、float []、またはComplex []入力のみを取りますが、オーディオファイルをバイト配列で読み取っているので、ちょっと混乱していますここからどこへ行く。私が見つけた唯一のものは、前の質問に対する答えです:

audiorecordを使用して特定の周波数の大きさを取得するためのAndroidオーディオFFT

しかし、これが正しい手順であるかどうかはわかりません。洞察力のある人はいますか?

4

2 に答える 2

14

代替手段はありません。ループを実行して、配列の各要素を個別にキャストする必要があります。

フロートとして fft するショーツに対しても同じことを行います。

public static float[] floatMe(short[] pcms) {
    float[] floaters = new float[pcms.length];
    for (int i = 0; i < pcms.length; i++) {
        floaters[i] = pcms[i];
    }
    return floaters;
}

コメントに基づいて2012年4月26日編集

本当に 16 ビットの PCM を持っていて、それを byte[] として持っている場合は、次のようにすることができます:

public static short[] shortMe(byte[] bytes) {
    short[] out = new short[bytes.length / 2]; // will drop last byte if odd number
    ByteBuffer bb = ByteBuffer.wrap(bytes);
    for (int i = 0; i < out.length; i++) {
        out[i] = bb.getShort();
    }
    return out;
}

それから

float[] pcmAsFloats = floatMe(shortMe(bytes));

そもそもバイト配列を提供する奇妙で設計の悪いクラスを使用していない限り、そのクラスの設計者は、Java がバイト (一度に 2 つ) を short に変換する方法と一致するようにバイトをパックする必要があります。

于 2012-04-25T23:39:05.460 に答える
-5
byte[] yourInitialData;
double[] yourOutputData = ByteBuffer.wrap(bytes).getDouble()
于 2012-04-25T23:40:04.697 に答える