将 Uint8(浮点AUDIO_F32)转换为int16_t(16 位 PCM)
Convert Uint8 (floating-point AUDIO_F32) to int16_t (16bit PCM)
我目前正在尝试录制音频并使用 SDL 进行处理,但在获取处理步骤所需的 16 位 PCM 音频时遇到了一些麻烦。我运行的设备仅支持 AUDIO_F32 格式。所以我的音频规格如下;
SDL_AudioSpec wanted;
SDL_zero(wanted);
wanted.freq = 48000;
wanted.format = AUDIO_F32SYS;
wanted.channels = 1;
wanted.samples = 4096;
wanted.callback = NULL;
现在我必须遵循包含录制音频的缓冲区;
std::vector<Uint8> buffered;
如何将Uint8
转换为 16 位 PCM 格式?如果我是对的,Uint8
应该是定义为unsigned char
的 32 位浮点音频。我已经尝试了下面的代码,但它似乎没有给出正确的结果;
std::vector<int16_t> pcm_buffer;
for( const Uint8& sample : buffered )
{
float sampleFloat = (float) sample;
sampleFloat *= 32767;
int16_t sampleInt = (int16_t) sampleFloat;
pcm_buffer.push_back(sampleInt);
}
我有一种感觉,我完全误解了我在做什么,所以我希望有人能指出我正确的方向。
F32 格式是 4 字节浮点数,但您将缓冲区作为字节缓冲区。您错过了首先将字节转换为浮点数的步骤。这是错误的行:
float sampleFloat = (float) sample
转换应操作在 4 字节块上,而不是单个字节上。比较:
std::vector<Uint8> buffered = ...;
std::vector<int16_t> pcm_buffer;
assert(buffered.size() % 4 == 0);
for(for size_t i = 0; i < buffered.size(); i += 4)
{
float sampleFloat = *(float*)(buffered.data() + i);
sampleFloat *= 32767;
int16_t sampleInt = (int16_t) sampleFloat;
pcm_buffer.push_back(sampleInt);
}
我认为由于对齐和混叠规则,assert(buffered.data() % 4 == 0)
也是合理的。
您还可以将强制转换本身置于循环之外并迭代浮点数组,例如
std::vector<Uint8> buffered = ...;
const float* p = (const float*)buffered.data();
const float* pe = p + buffered.size() / 4;
for (; p < pe; ++p) {
int16_t sampleInt = *p * 32767;
}
相关文章:
- C++ - 对 PCM::getInstance() 的未定义引用问题
- C++中饱和短 (int16)
- 将 Uint8(浮点AUDIO_F32)转换为int16_t(16 位 PCM)
- 捕获音频数据并保存到AudioFlinger中的原始PCM文件
- 如何将 WebM 文件解码为原始 PCM?
- 如何将 int16 数组更改为矢量<float>
- 将数组类型更改为 Int16 会节省存储空间吗?
- uint32, int16, uint8 .为什么这些常用的数据类型没有进入标准
- 在哪里可以从Android框架中获取原始的PCM数据
- INT16溢出导致无限循环
- 配置 AVCodecContext 结构以从原始 PCM 编码到 u-law
- 如何使用GStreamer播放PCM数据数组
- MPG123将mp3解码为C 中的PCM
- 如何使用IMFSinkWriter编写内存PCM数据
- INT16在C 上的二进制写作
- 如何在C++中为PCM缓冲音频添加音效
- 在 C/C+ 中从 16 位线性 PCM 音频转换为 32 位浮点数的最佳方法
- C++ 是使用 OpenAL 进行实时 PCM fft 音频处理
- 如何创建PCM签名的16位WAV文件
- C 关于Intel PCM源代码#ifndef intelpcm_api #define intelpcm_api