循环生成同名WAV文件时遇OSError:无法打开音频文件系统错误
解决循环生成同名WAV文件时的OSError系统错误
问题场景
循环生成32个同名WAV样本文件,前13轮循环执行正常,但第14轮处理第10个样本时抛出OSError,提示无法打开音频文件的系统错误。报错栈如下:
Traceback (most recent call last): File "main.py", line 68, in <module> a.train(dataloader, cfg.STAGE) File "/home/guest/trainer.py", line 255, in train save_RIR_results(real_Rcpu, fake, epoch, self.RIR_dir) File "/home/guest/utils.py", line 186, in save_RIR_results r = WaveWriter(real_Rpath, channels=1, samplerate=fs) File "/home/guest/miniconda3/envs/rir/lib/python3.6/site-packages/wavefile/wavefile.py", line 199, in __init__ filename, _sferrormessage(_lib.sf_error(self._sndfile)))) OSError: Error opening '../output/RIRsample10.wav': System error.
已确认目录路径正确,未找到同类问题解决方案。
排查与解决方案
1. 确保文件资源被正确释放
大概率是之前的WaveWriter实例未关闭,导致文件句柄泄漏,同名文件被系统锁定无法覆盖。建议使用上下文管理器(with语句)自动管理文件资源,避免手动关闭遗漏:
# 替换原创建WaveWriter的代码 with WaveWriter(real_Rpath, channels=1, samplerate=fs) as r: # 执行音频数据写入操作 r.write(real_Rcpu)
如果必须手动管理,务必在写入完成后调用r.close(),即使发生异常也要确保执行(可以用try...finally块)。
2. 处理文件系统临时锁定/权限问题
即使路径正确,系统可能因缓存延迟、杀毒软件扫描等临时锁定文件。可以在写入前先尝试删除已存在的文件,添加短暂重试机制:
import os import time real_Rpath = '../output/RIRsample10.wav' # 尝试清理已存在的文件 if os.path.exists(real_Rpath): for _ in range(3): # 最多重试3次 try: os.remove(real_Rpath) break except OSError: time.sleep(0.2) # 间隔200ms重试 # 再创建WaveWriter写入文件 r = WaveWriter(real_Rpath, channels=1, samplerate=fs) # ...后续写入逻辑
3. 替换为Python标准库wave模块
第三方wavefile库可能存在版本兼容问题(你使用的Python3.6较老),可以改用Python标准库wave模块实现WAV写入,避免依赖第三方库的潜在bug:
import wave import numpy as np # 假设real_Rcpu是numpy数组,需转换为符合WAV格式的字节流 # 示例:将浮点型数据转换为16位整型(根据你的实际采样格式调整) audio_data = (real_Rcpu * 32767).astype(np.int16) with wave.open(real_Rpath, 'wb') as wf: wf.setnchannels(1) # 单声道 wf.setsampwidth(2) # 16位采样宽度 wf.setframerate(fs) # 采样率 wf.writeframes(audio_data.tobytes())
4. 检查系统文件句柄限制
循环生成文件可能导致进程打开的文件句柄数量达到系统上限。在Linux系统中,可以通过以下命令查看当前进程的文件句柄使用情况:
lsof -p $(pidof python3) | wc -l
如果数量过高,需要排查代码中是否存在其他未释放的文件资源,或者临时调整进程的文件句柄限制(需系统权限)。
内容的提问来源于stack exchange,提问作者Halona
相关产品推荐
相关产品推荐

