一、Python所有方向的学习路线
Python所有方向的技术点做的整理,形成各个领域的知识点汇总,它的用处就在于,你可以按照下面的知识点去找对应的学习资源,保证自己学得较为全面。
二、Python必备开发工具
工具都帮大家整理好了,安装就可直接上手!
三、最新Python学习笔记
当我学到一定基础,有自己的理解能力的时候,会去阅读一些前辈整理的书籍或者手写的笔记资料,这些笔记详细记载了他们对一些技术点的理解,这些理解是比较独到,可以学到不一样的思路。
四、Python视频合集
观看全面零基础学习视频,看视频学习是最快捷也是最有效果的方式,跟着视频中老师的思路,从基础到深入,还是很容易入门的。
五、实战案例
纸上得来终觉浅,要学会跟着视频一起敲,要动手实操,才能将自己的所学运用到实际当中去,这时候可以搞点实战案例来学习。
六、面试宝典
简历模板
网上学习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。
一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!
# 按下 q 键可退出程序执行
if cv2.waitKey(20) & 0xFF == ord('q'):
break
最后,释放所有内容 (cv2.VideoCapture,并销毁创建的窗口):
capture.release()
cv2.destroyAllWindows()
通过在命令行中执行以下命令,运行脚本:
python read_camera.py 0
可以看到运行结果显示了相机获取的实时画面:
3.2 访问捕获画面对象的属性
可以使用 capture.get(property_identifier)
访问 capture
对象的某些属性,例如帧宽度、帧高度和每秒帧数 (Frames Per Second, FPS)。如果调用不受支持的属性,则返回值将为 0:
import cv2
capture = cv2.VideoCapture(0)
# 获取 VideoCapture 的属性 (frame width, frame height and frames per second (fps)):
frame_width = capture.get(cv2.CAP_PROP_FRAME_WIDTH)
frame_height = capture.get(cv2.CAP_PROP_FRAME_HEIGHT)
fps = capture.get(cv2.CAP_PROP_FPS)
# 打印属性值
print("CV\_CAP\_PROP\_FRAME\_WIDTH: '{}'".format(frame_width))
print("CV\_CAP\_PROP\_FRAME\_HEIGHT : '{}'".format(frame_height))
print("CAP\_PROP\_FPS : '{}'".format(fps))
# Check if camera opened successfully
if capture.isOpened()is False:
print("Error opening the camera")
while capture.isOpened():
ret, frame = capture.read()
if ret is True:
cv2.imshow('Input frame from the camera', frame)
if cv2.waitKey(20) & 0xFF == ord('q'):
break
else:
break
capture.release()
cv2.destroyAllWindows()
执行此脚本将会打印如下属性信息:
CV_CAP_PROP_FRAME_WIDTH: '640.0'
CV_CAP_PROP_FRAME_HEIGHT : '480.0'
CAP_PROP_FPS : '30.0'
3.3 保存相机画面
可以修改前面的示例以在处理流程中添加其他的功能。例如,我们可能想将一些关键的感兴趣帧保存到磁盘中。在以下示例 read_camera_capture.py
中 ,将添加此示例功能,当按下键盘上的 c
键时,将当前帧保存到磁盘(同时保存 BGR 和灰度帧):
import cv2
import argparse
capture = cv2.VideoCapture(0)
if capture.isOpened() is False:
print("Error opening the camera")
frame_index = 0
while capture.isOpened():
ret, frame = capture.read()
if ret is True:
gray_frame = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
# 保存相机画面
if cv2.waitKey(20) & 0xFF == ord('c'):
frame_name = "camera\_frame\_{}.png".format(frame_index)
gray_frame_name = "grayscale\_camera\_frame\_{}.png".format(frame_index)
# 将当前帧保存到磁盘(同时保存 BGR 和灰度帧)
cv2.imwrite(frame_name, frame)
cv2.imwrite(gray_frame_name, gray_frame)
frame_index += 1
if cv2.waitKey(20) & 0xFF == ord('q'):
break
else:
break
capture.release()
cv2.destroyAllWindows()
当按下 c
键时,首先构造两个文件名;然后,将两个图像保存到磁盘;最后,frame_index
递增,以便为保存下一帧做好准备。
3.4 读取视频文件
cv2.VideoCapture
也可以用于读取视频文件,要读取视频文件,应在创建 cv2.VideoCapture
对象时提供视频文件的路径,编写 read_video_file.py
脚本:
import cv2
import argparse
parser = argparse.ArgumentParser()
parser.add_argument("video\_path", help="path to the video file")
args = parser.parse_args()
capture = cv2.VideoCapture(args.video_path)
if capture.isOpened() is False:
print("Error opening the video file!")
while capture.isOpened():
ret, frame = capture.read()
if ret is True:
cv2.imshow('Original frame from the video file', frame)
gray_frame = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
cv2.imshow('Grayscale frame', gray_frame)
if cv2.waitKey(20) & 0xFF == ord('q'):
break
else:
break
capture.release()
cv2.destroyAllWindows()
通过在命令行中执行以下命令,运行脚本:
python read_video_file.py xinlingqilv.mp4
可以看到运行结果开始播放视频文件:
3.5 读取 IP 摄像机
cv2.VideoCapture
也可以从 IP 摄像头读取数据。在 OpenCV 中从 IP 摄像头读取数据与从文件读取数据非常相似。唯一需要修改的是提供给 cv2.VideoCapture
构造函数的参数。可以使用本地网络中的 IP 摄像机或尝试连接公共 IP 摄像机。
4. 保存视频文件
接下来,首先介绍与视频相关的基本概念(例如,fps、编解码器和视频文件格式等),然后将了解如何使用 cv2.VideoWriter
保存视频文件。
4.1 计算帧率(FPS)
FPS
是计算机视觉项目中的一个重要指标,该指标表示每秒处理的帧(画面)数,FPS
越高越好。但是,算法每秒应处理的帧数将取决于需要解决的特定问题。例如,如果算法需要跟踪和检测在街上行走的人,那么 15 FPS 可能就足够了。但是,如果是检测和跟踪高速公路上快速行驶的汽车,则可能需要 20-25 FPS。
因此,计算计算机视觉项目中的 FPS 指标非常重要。编写 read_camera_fps.py
以输出 FPS
:
import cv2
import argparse
import time
capture = cv2.VideoCapture(0)
if capture.isOpened() is False:
print("Error opening the camera")
while capture.isOpened():
ret, frame = capture.read()
if ret is True:
processing_start = time.time()
cv2.imshow("Input frame from the camera", frame)
gray_frame = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
cv2.imshow('Grayscale input camera', gray_frame)
if cv2.waitKey(20) & 0xFF == ord('q'):
break
processing_end = time.time()
processing_time_frame = processing_end - processing_start
print("FPS: {}".format(1.0 / processing_time_frame))
else:
break
capture.release()
cv2.destroyAllWindows()
在上述示例脚本中,首先需要获取处理开始的时间:
processing_start = time.time()
然后,获取所有处理完成后的时间:
processing_end = time.time()
接下来,计算时间差:
processing_time_frame = processing_end - processing_start
最后,计算并打印 FPS:
print("FPS: {}".format(1.0 / processing_time_frame))
4.2 写入视频文件的流程
视频编码是一种用于压缩和解压缩数字视频的程序。具体而言,编解码器可用于将未压缩的视频转换为压缩后的视频,或者可用于将压缩的视频转换为未压缩的视频。压缩视频格式通常遵循视频压缩规范或视频编码格式的标准规范。OpenCV 提供了 FOURCC
(一个 4 字节编码),用于指定视频编解码器,查看可用编码列表获取更多可用编码。应该注意的是:支持的编解码器是平台相关的,如果想使用特定的编解码器,则应该在系统上安装该编解码器。典型的编解码器包括 DIVX、XVID、X264 和 MJPG。
视频文件格式是一种用于存储数字视频数据的文件格式,典型的视频文件格式包括 AVI(*.avi)、MP4(*.mp4)、QuickTime(*.mov) 和 Windows Media Video(*.wmv)。
最后,应该考虑到视频文件格式和 FOURCC 之间需要进行正确的组合。 在 OpenCV 中创建视频文件时,必须考虑这些因素:
上图总结了在 OpenCV 中使用 cv2.VideoWriter()
创建视频文件时应考虑的主要因素。在创建的名为 video_example.avi
视频中,FOURCC 值为 XVID,视频文件格式为 AVI(*.avi),同时最后,应设置视频每一帧的 FPS 和尺寸。
脚本 write_video_file.py
演示如何创建视频文件:
# Import required packages
import cv2
import argparse
parser = argparse.ArgumentParser()
parser.add_argument("output\_video\_path", help="path to the video file to write")
args = parser.parse_args()
capture = cv2.VideoCapture(0)
frame_width = capture.get(cv2.CAP_PROP_FRAME_WIDTH)
frame_height = capture.get(cv2.CAP_PROP_FRAME_HEIGHT)
fps = capture.get(cv2.CAP_PROP_FPS)
fourcc = cv2.VideoWriter_fourcc(\*'XVID')
out_gray = cv2.VideoWriter(args.output_video_path, fourcc, int(fps), (int(frame_width), int(frame_height)), False)
while capture.isOpened():
ret, frame = capture.read()
if ret:
gray_frame = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
out_gray.write(gray_frame)
cv2.imshow('gray', gray_frame)
if cv2.waitKey(1) & 0xFF == ord('q'):
break
else:
break
capture.release()
out_gray.release()
cv2.destroyAllWindows()
在上例中,必需的参数是输出视频文件名(例如 video_example.avi):
parser = argparse.ArgumentParser()
parser.add_argument("output\_video\_path", help="path to the video file to write")
args = parser.parse_args()
从连接到计算机的第一台相机拍摄视频画面。因此,首先创建对象:
capture = cv2.VideoCapture(0)
接下来,从 capture
对象中获取一些关键属性(帧宽度、帧高度和 FPS),用于创建视频文件时使用:
frame_width = capture.get(cv2.CAP_PROP_FRAME_WIDTH)
frame_height = capture.get(cv2.CAP_PROP_FRAME_HEIGHT)
fps = capture.get(cv2.CAP_PROP_FPS)
然后,使用四字节编码 FOURCC
指定视频编解码器,此处将编解码器定义为 XVID :
fourcc = cv2.VideoWriter_fourcc('X', 'V', 'I', 'D')
也可以使用以下方式指定视频编码器:
fourcc = cv2.VideoWriter_fourcc(\*'XVID')
然后,使用与输入相机相同的属性创建 cv2.VideoWriter
对象 out_gray
,cv2.VideoWriter
的最后一个参数值是 False 表示以灰度方式写入视频。如果我们想创建彩色视频,最后一个参数值为 True :
out_gray = cv2.VideoWriter(args.output_video_path, fourcc, int(fps), (int(frame_width), int(frame_height)), False)
使用 capture.read()
从 catpure
对象获取相机帧,每一帧都被转换成灰度并写入视频文件,如果按下 q
键,程序结束:
while capture.isOpened():
ret, frame = capture.read()
if ret:
gray_frame = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
out_gray.write(gray_frame)
cv2.imshow('gray', gray_frame)
if cv2.waitKey(1) & 0xFF == ord('q'):
break
else:
break
最后,释放所有内容(包括 cv2.VideoCapture
和 cv2.VideWriter
对象,并销毁创建的窗口):
capture.release()
out_gray.release()
cv2.destroyAllWindows()
通过在命令行中执行以下命令,运行脚本:
python write_video_file.py video_example.avi
在工作目录下可以看到保存的灰度视频文件。
5. 视频属性详解
在上述示例中,我们已经了解了如何从 cv2.VideoCapture
对象中获取一些关键属性。接下来,将介绍所有属性并了解它们的工作原理。最后,我们将使用这些属性来加载视频文件并反向输出(首先显示视频的最后一帧,依此类推)。
5.1 获取视频对象的属性
创建 read_video_file_all_properties.py
脚本来显示所有属性。其中一些属性仅在使用相机时才有效(而在视频文件时无效)。
在脚本中,首先创建 decode_fourcc()
函数,它将 capture.get(cv2.CAP_PROP_FOURCC)
返回的 int
类型的值转换为表示编解码器的字符串值,来正确输出编解码器:
def decode\_fourcc(fourcc):
fourcc_int = int(fourcc)
print("int value of fourcc: '{}'".format(fourcc_int))
fourcc_decode = ""
for i in range(4):
int_value = fourcc_int >> 8 \* i & 0xFF
print("int\_value: '{}'".format(int_value))
fourcc_decode += chr(int_value)
return fourcc_decode
下图解释了函数 decode_fourcc
的工作原理:
第一步是获取由 capture.get(cv2.CAP_PROP_FOURCC) 返回的值( int 表示的字符串),然后,迭代四次,每次获取八位并将这八位转换为 int 。最后,使用 chr() 函数将这些 int 值转换为 char。也可以只使用一行代码就可以完成此功能:
return "".join([chr((fourcc_int >> 8 * i) & 0xFF) for i in range(4)])
下表显示了视频文件的主要属性和解释:
视频属性 | 解释 |
---|---|
CAP_PROP_POS_FRAMES | 视频文件的当前帧 |
CAP_PROP_POS_MSEC | 当前帧的时间戳 |
CAP_PROP_FPS | 获取 FPS |
CAP_PROP_FRAME_WODTH | 视频帧的宽度 |
CAP_PROP_FRAME_HEIGHT | 视频帧的高度 |
CAP_PROP_FRAME_COUNT | 视频文件的总帧数 |
使用以下代码,可以获取和打印所有属性:
print("CV\_CAP\_PROP\_FRAME\_WIDTH:'{}'".format(capture.get(cv2.CAP_PROP_FRAME_WIDTH)))
print("CV\_CAP\_PROP\_FRAME\_HEIGHT :'{}'".format(capture.get(cv2.CAP_PROP_FRAME_HEIGHT)))
print("CAP\_PROP\_FPS : '{}'".format(capture.get(cv2.CAP_PROP_FPS)))
print("CAP\_PROP\_POS\_MSEC :'{}'".format(capture.get(cv2.CAP_PROP_POS_MSEC)))
print("CAP\_PROP\_POS\_FRAMES :'{}'".format(capture.get(cv2.CAP_PROP_POS_FRAMES)))
print("CAP\_PROP\_FOURCC :'{}'".format(decode_fourcc(capture.get(cv2.CAP_PROP_FOURCC))))
print("CAP\_PROP\_FRAME\_COUNT :'{}'".format(capture.get(cv2.CAP_PROP_FRAME_COUNT)))
print("CAP\_PROP\_MODE : '{}'".format(capture.get(cv2.CAP_PROP_MODE)))
print("CAP\_PROP\_BRIGHTNESS :'{}'".format(capture.get(cv2.CAP_PROP_BRIGHTNESS)))
print("CAP\_PROP\_CONTRAST :'{}'".format(capture.get(cv2.CAP_PROP_CONTRAST)))
print("CAP\_PROP\_SATURATION :'{}'".format(capture.get(cv2.CAP_PROP_SATURATION)))
print("CAP\_PROP\_HUE : '{}'".format(capture.get(cv2.CAP_PROP_HUE)))
print("CAP\_PROP\_GAIN : '{}'".format(capture.get(cv2.CAP_PROP_GAIN)))
print("CAP\_PROP\_EXPOSURE :'{}'".format(capture.get(cv2.CAP_PROP_EXPOSURE)))
print("CAP\_PROP\_CONVERT\_RGB :'{}'".format(capture.get(cv2.CAP_PROP_CONVERT_RGB)))
print("CAP\_PROP\_RECTIFICATION :'{}'".format(capture.get(cv2.CAP_PROP_RECTIFICATION)))
print("CAP\_PROP\_ISO\_SPEED :'{}'".format(capture.get(cv2.CAP_PROP_ISO_SPEED)))
print("CAP\_PROP\_BUFFERSIZE :'{}'".format(capture.get(cv2.CAP_PROP_BUFFERSIZE)))
5.2 视频属性的使用——视频的反向播放
为例更好的了解如何使用上述属性,接下来,我们通过实战使用这些属性。编写 read_video_file_backwards.py
脚本,该脚本使用一些上述属性加载视频并反向播放(首先显示视频的最后一帧,然后播放倒数第二帧,依此类推),为了实现此目的,需要使用属性:cv2.CAP_PROP_FRAME_COUNT
和 cv2.CAP_PROP_POS_FRAMES
。
import cv2
import argparse
parser = argparse.ArgumentParser()
parser.add_argument("video\_path", help='path to the video fiel')
args = parser.parse_args()
capture = cv2.VideoCapture(args.video_path)
if capture.isOpened() is False:
print("Error opening vieo stream or file")
frame_index = capture.get(cv2.CAP_PROP_FRAME_COUNT) - 1
print("Starting in frame: '{}'".format(frame_index))
while capture.isOpened() and frame_index >= 0:
capture.set(cv2.CAP_PROP_POS_FRAMES, frame_index)
ret, frame = capture.read()
if ret:
cv2.imshow('Original frame', frame)
frame_index = frame_index - 1
print("next index to read: '{}'".format(frame_index))
# Press q on keyboard to exit the program:
if cv2.waitKey(25) & 0xFF == ord('q'):
break
# Break the loop
else:
break
capture.release()
cv2.destroyAllWindows()
第一步是获取最后一帧的索引:
frame_index = capture.get(cv2.CAP_PROP_FRAME_COUNT) - 1
然后,将当前帧设置为所获取帧的位置:
capture.set(cv2.CAP_PROP_POS_FRAMES, frame_index)
这样,就可以像读取获取都帧了:
ret, frame = capture.read()
最后,索引值减一以从视频文件中读取下一帧:
frame_index = frame_index - 1
通过运行以下命令就可以看到反向播放的视频:
一、Python所有方向的学习路线
Python所有方向路线就是把Python常用的技术点做整理,形成各个领域的知识点汇总,它的用处就在于,你可以按照上面的知识点去找对应的学习资源,保证自己学得较为全面。
二、学习软件
工欲善其事必先利其器。学习Python常用的开发软件都在这里了,给大家节省了很多时间。
三、入门学习视频
我们在看视频学习的时候,不能光动眼动脑不动手,比较科学的学习方法是在理解之后运用它们,这时候练手项目就很适合了。
网上学习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。
一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!