Вопрос по fft, android, java – Как преобразовать 16-битный байтовый массив PCM в массив double или float?
Я пытаюсь выполнить быстрое преобразование Фурье для аудиофайла .3gpp. Файл содержит небольшую 5-секундную запись с частотой 44100 кГц от микрофона телефона.
Каждый алгоритм Java FFT, который я могу найти, по понятным причинам принимает только входы double [], float [] или Complex [], но я читаю аудиофайл в байтовом массиве, так что я немного запутался в том, что куда я иду отсюда Единственное, что я смог найти - это ответ на предыдущий вопрос:
Android аудио 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;
}
EDIT 4/26/2012 based on comments
Если у вас действительно есть 16-битный PCM, но он есть как байт [], то вы можете сделать это:
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 за раз) в шорты.
byte[] yourInitialData;
double[] yourOutputData = ByteBuffer.wrap(bytes).getDouble()
getDouble()
возвращает типdouble
неdouble[]
, Это останавливает компиляцию. - getDouble () захватывает 4 байта за раз, связывает их вместе в 32-битные и интерпретирует все какdouble
, Поскольку байтовый массив не был сохранен какdouble
s, это приведет к бессмысленным результатам, и только 1/2double
s можно извлечь из массива, как былоshort
S положить в массив. - Смотрите мой ответ выше для способа использования ByteBuffer для преобразованияbyte[]
вshort[]
это работает.