python-3.x - 使用 librosa.resample 后出现“wave.Error:未知格式:3”。librosa 的输出有什么问题吗?
问题描述
我有一个采样率为 44.1khz 的 .wav 文件,我想使用 librosa.resample 将其重新采样为 16khz。虽然 output.wav 听起来很棒,而且是 16khz,但是当我尝试通过 wave.open 读取它时出现错误。
这个问题和我的很相似: Open a wave file in python: unknown format: 49. What's going wrong?
这是我的代码:
if __name__ == "__main__":
input_wav = '1d13eeb2febdb5fc41d3aa7db311fa33.wav'
output_wav = 'result.wav'
y, sr = librosa.load(input_wav, sr=None)
print(sr)
y = librosa.resample(y, orig_sr=sr, target_sr=16000)
librosa.output.write_wav(output_wav, y, sr=16000)
wave.open(output_wav)
我在最后一步出错了wave.open(output_wav)
例外情况如下:
Traceback (most recent call last):
File "/Users/range/Code/PycharmProjects/Speaker/test.py", line 204, in <module>
wave.open(output_wav)
File "/Library/Frameworks/Python.framework/Versions/3.6/lib/python3.6/wave.py", line 499, in open
return Wave_read(f)
File "/Library/Frameworks/Python.framework/Versions/3.6/lib/python3.6/wave.py", line 163, in __init__
self.initfp(f)
File "/Library/Frameworks/Python.framework/Versions/3.6/lib/python3.6/wave.py", line 143, in initfp
self._read_fmt_chunk(chunk)
File "/Library/Frameworks/Python.framework/Versions/3.6/lib/python3.6/wave.py", line 260, in _read_fmt_chunk
raise Error('unknown format: %r' % (wFormatTag,))
wave.Error: unknown format: 3
我只是不知道为什么不能 wave.open 读取 wav_flie,我必须重新采样 wav 才能做进一步的工作。
我想知道是否librosa.output.write
改变了wav的类型。
所以我必须自己写resample函数。幸运的是,它有效。这是我的代码:
def resample(input_wav, output_wav, tar_fs=16000):
audio_file = wave.open(input_wav, 'rb')
audio_data = audio_file.readframes(audio_file.getnframes())
audio_data_short = np.fromstring(audio_data, np.short)
src_fs = audio_file.getframerate()
dtype = audio_data_short.dtype
audio_len = len(audio_data_short)
audio_time_max = 1.0*(audio_len-1) / src_fs
src_time = 1.0 * np.linspace(0, audio_len, audio_len) / src_fs
tar_time = 1.0 * np.linspace(0, np.int(audio_time_max*tar_fs), np.int(audio_time_max*tar_fs)) / tar_fs
output_signal = np.interp(tar_time, src_time, audio_data_short).astype(dtype)
with wave.open(output_wav, 'wb') as f:
f.setnchannels(1)
f.setsampwidth(2)
f.setframerate(tar_fs)
f.writeframes(output_signal)
我希望你能帮助我理解在 librosa 重新采样 wav 时出了什么问题,我很高兴看到我的代码可以帮助其他有同样问题的人。:)
解决方案
我正在研究一个项目并且遇到了同样的错误,所以稍微挖掘了一下,发现问题是由于 librosa 在输出模块中使用 write_wav() 写入波形文件的默认方式。
问题是编码量化是 24 位,因为它是“浮点 PCM”。您可以使用SoX轻松更改位量化。SoX 是跨平台命令行实用程序,您可以使用它来控制编码格式等细节。
例如,你会做这样的事情来从 24 位编码到 16 位编码:
sox audio.wav -b 16 -e signed-integer modified_audio.wav
推荐阅读
- tomcat - 如何配置 tomcat 以提供预压缩的静态文件?
- c - fgets 是存储换行符还是仅存储 \0?
- python-3.x - 如何将计算列添加到 Pandas 数据框中?
- python-3.x - 提高 Brocard 问题的复杂性?
- java - Java Swing:如何在自定义的 Jbutton 上设置文本?
- gcc - 如何更改 GNU GCC 的默认搜索路径值以供常规使用?
- python - 为 Tesseract OCR 清理照片的方法?
- java - java - 无法访问将方法返回给另一个方法的java?
- javascript - 如何对不同类别的 Select2 标签进行分组
- python-3.x - 尝试使用创建表单时,{{form.as_table}} 的 django 模板出错