使用cv2.VideoCapture处理MP4视频时遇resize断言失败问题求助
问题分析与解决
这个报错!ssize.empty()是因为调用cv2.resize时传入的frame是空的,根源出在这几个地方:
- 循环里没判断
cap.read()的返回值ret,当视频读到最后一帧后,ret会变成False,此时frame是None,再执行resize就触发断言错误。 - 用字符串拼接路径容易出问题,比如源/目标目录末尾有没有斜杠都会影响,应该用
os.path.join处理路径。 - 目标目录如果不存在,
cv2.VideoWriter无法写入,得先确保目录存在。 - 没有过滤非MP4文件,
os.listdir会返回目录里所有文件,比如隐藏文件、其他格式文件,这些文件VideoCapture打不开,后续处理必然报错。 - 就算
cap.isOpened()返回False,代码还是会继续执行后面的循环,直接导致报错。
修正后的代码
import cv2 import numpy as np import os source = "C:\\Users\\Desktop\\sourcedir" dest = r"C:\Users\Desktop\dest" # 先创建目标目录,不存在则自动创建 os.makedirs(dest, exist_ok=True) def frame_capture(file): # 只处理MP4格式文件,跳过其他类型 if not file.lower().endswith('.mp4'): print(f"跳过非MP4文件: {file}") return # 用os.path.join安全拼接路径,避免分隔符问题 src_path = os.path.join(source, file) dest_path = os.path.join(dest, file) cap = cv2.VideoCapture(src_path) if not cap.isOpened(): print(f"无法打开视频文件: {src_path}") return # 获取原视频帧率,不用硬写25,适配不同视频 fps = cap.get(cv2.CAP_PROP_FPS) # 如果获取帧率失败,默认用25 if fps <= 0: fps = 25 # 初始化视频写入器 result = cv2.VideoWriter( dest_path, cv2.VideoWriter_fourcc(*'mp4v'), fps, (227, 227) ) while True: ret, frame = cap.read() # 读取失败(视频读完)就退出循环 if not ret: break # 调整帧尺寸并写入 resized_frame = cv2.resize(frame, (227, 227)) result.write(resized_frame) # 释放所有资源 cap.release() result.release() cv2.destroyAllWindows() print(f"处理完成: {dest_path}") for file in os.listdir(source): frame_capture(file)
关键修改点说明
- 新增目标目录创建:用
os.makedirs确保目标目录存在,避免写入失败。 - 过滤非MP4文件:只处理
.mp4后缀的文件,跳过无关文件。 - 路径拼接改用
os.path.join:自动适配系统路径分隔符,避免手动拼接出错。 - 增加
ret判断:每次读取帧后先检查是否成功读取,读到视频末尾就退出循环。 - 动态获取原视频帧率:保证输出视频的播放速度和原视频一致,不用硬写固定值。
- 严谨释放资源:确保
VideoWriter也被释放,避免内存泄漏。
内容的提问来源于stack exchange,提问作者M P
相关产品推荐
相关产品推荐

