如何将.WAV音频数据样本转换为double类型?

时间:2021-12-20 19:41:09

I'm working on an application that processes audio data. I'm using java (I've added MP3SPI, Jlayer, and Tritonus). I'm extracting the audio data from a .wav file to a byte array. The audio data samples I'm working with are 16 bits stereo.

我正在研究处理音频数据的应用程序。我正在使用java(我添加了MP3SPI,Jlayer和Tritonus)。我正在将.wav文件中的音频数据提取到字节数组中。我正在使用的音频数据样本是16位立体声。

According to what I've read the format for one sample is:

根据我所读到的,一个样本的格式是:

AABBCCDD

where AABB represents left channel and CCDD rigth channel (2 bytes for each channel). I'd need to convert this sample into a double value type. I've reading about data format. Java uses Big endian, .wav files use little endian. I'm a little bit confused. Could you please help me with the conversion process? Thanks you all

其中AABB代表左通道和CCDD rigth通道(每个通道2个字节)。我需要将此示例转换为double值类型。我正在阅读有关数据格式的内容。 Java使用Big endian,.wav文件使用little endian。我有点困惑。你能帮我转换一下吗?谢谢大家

4 个解决方案

#1


Warning: integers and bytes are signed. Maybe you need to mask the low bytes when packing them together:

警告:整数和字节都已签名。也许你需要在将它们打包在一起时屏蔽低字节:

for (int i =0; i < length; i += 4) {
    double left = (double)((bytes [i] & 0xff) | (bytes[i + 1] << 8));
    double right = (double)((bytes [i + 2] & 0xff) | (bytes[i + 3] << 8));

    ... your code here ...

}

#2


When you use the ByteBuffer (java.nio.ByteBuffer) you can use the method order;

当您使用ByteBuffer(java.nio.ByteBuffer)时,您可以使用方法顺序;

[order]

public final ByteBuffer order(ByteOrder bo)

公共最终ByteBuffer订单(ByteOrder bo)

Modifies this buffer's byte order.

Parameters:
    bo - The new byte order, either BIG_ENDIAN or LITTLE_ENDIAN
Returns:
    This buffer

After this you can get the above mentioned values with;

在此之后,您可以获得上述值;

getChar() getShort() getInt() getFloat() getDouble()

getChar()getShort()getInt()getFloat()getDouble()

What a great language is Java ;-)

多么好的语言是Java ;-)

#3


Little Endian means that the data is in the form BBAA and DDCC. You would just swap it around.

Little Endian表示数据采用BBAA和DDCC格式。你只需要换掉它。

From the beginning of the frame:

从框架的开头:

int left = (bytes[i+1] << 8) + bytes[i];
int right = (bytes[i+3] << 8) + bytes[i+2];

where i is your the index of your sample.

其中i是您的样本索引。

#4


I would personally look for a library that does the endian swapping for you. Each audio file format has assumptions about the endianness for you and getting this right is tricky for all the bit depths/datatypes wave files support:

我个人会寻找一个为您进行endian交换的库。每种音频文件格式都有关于字节序的假设,对于所有位深度/数据类型的波形文件支持,正确处理这种情况很棘手:

  • 8bit - uint8
  • 8位 - uint8

  • 16bit - int16
  • 16位 - int16

  • 24bit - int32
  • 24位 - int32

  • 32bit - int32 as float
  • 32bit - int32 as float

  • 32bit - float
  • 32位 - 浮动

  • 64bit - double
  • 64位 - 双倍

If you want to support most common types of wave files you'll need endian conversions for all of these datatypes.

如果要支持大多数常见类型的波形文件,则需要对所有这些数据类型进行字节序转换。

I would look at ByteSwapper, which will give you byteswapping for most of the types listed above.

我会看看ByteSwapper,它会为你提供上面列出的大多数类型的byteswapping。

Its too bad Java doesn't have an endianness field in their File IO classes. Being able to simply open a file whos edianness is big or little is a much easier solution to this issue.

它太糟糕的Java在它们的File IO类中没有endianness字段。能够简单地打开edianness大或小的文件是解决这个问题的一个更容易的解决方案。

#1


Warning: integers and bytes are signed. Maybe you need to mask the low bytes when packing them together:

警告:整数和字节都已签名。也许你需要在将它们打包在一起时屏蔽低字节:

for (int i =0; i < length; i += 4) {
    double left = (double)((bytes [i] & 0xff) | (bytes[i + 1] << 8));
    double right = (double)((bytes [i + 2] & 0xff) | (bytes[i + 3] << 8));

    ... your code here ...

}

#2


When you use the ByteBuffer (java.nio.ByteBuffer) you can use the method order;

当您使用ByteBuffer(java.nio.ByteBuffer)时,您可以使用方法顺序;

[order]

public final ByteBuffer order(ByteOrder bo)

公共最终ByteBuffer订单(ByteOrder bo)

Modifies this buffer's byte order.

Parameters:
    bo - The new byte order, either BIG_ENDIAN or LITTLE_ENDIAN
Returns:
    This buffer

After this you can get the above mentioned values with;

在此之后,您可以获得上述值;

getChar() getShort() getInt() getFloat() getDouble()

getChar()getShort()getInt()getFloat()getDouble()

What a great language is Java ;-)

多么好的语言是Java ;-)

#3


Little Endian means that the data is in the form BBAA and DDCC. You would just swap it around.

Little Endian表示数据采用BBAA和DDCC格式。你只需要换掉它。

From the beginning of the frame:

从框架的开头:

int left = (bytes[i+1] << 8) + bytes[i];
int right = (bytes[i+3] << 8) + bytes[i+2];

where i is your the index of your sample.

其中i是您的样本索引。

#4


I would personally look for a library that does the endian swapping for you. Each audio file format has assumptions about the endianness for you and getting this right is tricky for all the bit depths/datatypes wave files support:

我个人会寻找一个为您进行endian交换的库。每种音频文件格式都有关于字节序的假设,对于所有位深度/数据类型的波形文件支持,正确处理这种情况很棘手:

  • 8bit - uint8
  • 8位 - uint8

  • 16bit - int16
  • 16位 - int16

  • 24bit - int32
  • 24位 - int32

  • 32bit - int32 as float
  • 32bit - int32 as float

  • 32bit - float
  • 32位 - 浮动

  • 64bit - double
  • 64位 - 双倍

If you want to support most common types of wave files you'll need endian conversions for all of these datatypes.

如果要支持大多数常见类型的波形文件,则需要对所有这些数据类型进行字节序转换。

I would look at ByteSwapper, which will give you byteswapping for most of the types listed above.

我会看看ByteSwapper,它会为你提供上面列出的大多数类型的byteswapping。

Its too bad Java doesn't have an endianness field in their File IO classes. Being able to simply open a file whos edianness is big or little is a much easier solution to this issue.

它太糟糕的Java在它们的File IO类中没有endianness字段。能够简单地打开edianness大或小的文件是解决这个问题的一个更容易的解决方案。