近期有个任务需要实时检测出视频中的某个目标,这里我用的是神经网络,所以需要有训练样本,那就将视频的每一帧提取出来保存成图像去进行学习。
首先最先想到的是Opencv中的cv2.VideoCapture(video_path).read(),我是这样写的:
import cv2 as cv
def totalnumber_of_videoframes(video_path):
capture = cv.VideoCapture(video_path)
len_video_frame = int(capture.get(cv.CAP_PROP_FRAME_COUNT))
print('total number of video frames :', len_video_frame)
n = 0
loss_frames = []
for i in range(len_video_frame):
ret,frame = capture.read() #ret返回的是True或者False,代表有没有读取到图像
if ret:
n += 1
else:
print("loss this frame")
loss_frames.append(i)
print('index :{}, read: {}'.format(i, n))
print(loss_frames)
def vidio_frame_extract(video_path,save_path,index):
capture = cv.VideoCapture(video_path)
while capture.isOpened():
ret,frame = capture.read()#frame是BGR格式
if not ret:
print('loss this frame')
if frame is None:
break
print(frame.shape) #(795, 1055, 3)
cv.imshow('frame',frame)
save_frame = "{}/{:>03d}.bmp".format(save_path, index)
cv.imwrite(save_frame,frame)
index = index+1
capture.release()
cv.destroyAllWindows()
if __name__ == "__main__":
video_path = "F:\object_detection\dog.avi"
save_path = "F:\object_detection\dog"
index = 0
totalnumber_of_videoframes(video_path)#先看一下视频本身实际有多少帧,再看真正保存的视频帧有多少
vidio_frame_extract(video_path, save_path, index)
结果发现我提取出来的视频帧数与视频本身实际的帧数不相同!!!即OpenCV使用VideoCapture处理视频时会丢失掉最后一些帧。
原因:可能是因为VideoCapture会忽略掉重复的帧,所以在调用VideoCapture时实际得到的帧数会近似等于视频实际的总帧数减去重复帧数。
解决方法:
利用python的一个视频处理库scikit-video,使用skvideo.io.vreader()可以逐帧加载任意视频
首先 pip install scikit-video
import cv2 as cv
import skvideo
from skvideo import io
def vidio_frame_extract(video_path,save_path,index):
capture = skvideo.io.vreader(video_path)
for frame in capture:#frame是RGB格式
frame = cv.cvtColor(frame,cv.COLOR_RGB2BGR)
cv.imshow("frame",frame)
save_frame = "{}/{:>03d}.bmp".format(save_path, index)
cv.imwrite(save_frame,frame)#注意cv.imwrite只有对frame为BGR空间时,才写出正确颜色空间图片
index = index+1
if __name__ == "__main__":
video_path = "F:\object_detection\dog.avi"
save_path = "F:\object_detection\dog"
index = 0
vidio_frame_extract(video_path, save_path, index)
小插曲:这里出现了一个报错: AssertionError: Cannot find installation of ffmpeg.
解决:conda install ffmpeg(不知道为什么pip install ffmpeg没有用)