Чтение WAV-файла Java против Matlab - PullRequest
4 голосов
/ 08 февраля 2012

Я пытаюсь прочитать данные файла .wav как в java, так и в matlab и сохранить как массив байтов.

В Java код выглядит следующим образом:

 public byte[] readWav2(File file) throws UnsupportedAudioFileException, IOException {

     AudioFormat audioFormat;

     AudioInputStream inputAIS = AudioSystem.getAudioInputStream(file);
     audioFormat = inputAIS.getFormat();
     ByteArrayOutputStream baos = new ByteArrayOutputStream();

     // Read the audio data into a memory buffer.
     int nBufferSize = BUFFER_LENGTH * audioFormat.getFrameSize();


        byte[] abBuffer = new byte[nBufferSize];
        while (true) {

            int nBytesRead = inputAIS.read(abBuffer);

            if (nBytesRead == -1) {
                break;
            }
            baos.write(abBuffer, 0, nBytesRead);
        }

        byte[] abAudioData = baos.toByteArray();


        return abAudioData;
    }

В Matlab я использую функцию wavread:

[Y, FS] = wavread('sound.wav', 'native');

Но результаты, которые я получаю, разные.

В Java первые 20 байтов:

53, 0, 19, 0, -71, -1, -80, -1, -99, -1, 10, 0, 87, 0, -69, -1, 123, -1, -77, -1

В матлабе:

53, 19, -71, -80, -99, 10, 87, -69, -133, -77, 38, 143, 13, -100, 39, 45, -52, -83, -82, 56

Почему каждый второй байт в java равен 0 или -1, а в matlab его нет? Даже если я пропущу 0 и -1, где в Java есть 123 для Matlab есть -133? Почему это отличается?

1 Ответ

5 голосов
/ 08 февраля 2012

Java возвращает вам 16-битные подписанные данные PCM. Поскольку каждая выборка составляет 16 битов, а байт содержит 8 битов, каждая выборка занимает два байта в Java. Matlab возвращает вам массив из 16-битных сэмплов напрямую.

В основном, данные одинаковы. Это просто по-другому выложено в памяти.

Чтобы получить более простой доступ к образцам из Java, вы можете выполнить некоторую побитовую арифметику, например:

int firstSample = (abAudioData[0]&0xFF) | (abAudioData[1]<<8);

Другой способ прочитать примеры - использовать буферы java.nio:

ByteBuffer bb = ByteBuffer.wrap(abAudioData);
bb.order(ByteOrder.LITTLE_ENDIAN);
ShortBuffer sb = bb.asShortBuffer();

int firstSample = sb.get();
...