目标
- 衡量代码的性能。
- 一些提高代码性能的技巧。
- 你将看到以下功能:cv.getTickCount,cv.getTickFrequency等。
使用OpenCV衡量性能 cv.getTickCount函数返回从参考事件(如打开机器的那一刻)到调用此函数那一刻之间的时钟周期数。因此,如果在函数执行之前和之后调用它,则会获得用于执行函数的时钟周期数。
cv.getTickFrequency函数返回时钟周期的频率或每秒的时钟周期数。因此,要找到执行时间(以秒为单位),你可以执行以下操作:
e1 = cv.getTickCount()
# 你的执行代码
e2 = cv.getTickCount()
time = (e2 - e1)/ cv.getTickFrequency()
下面是一个例子
path = r'D:\Laboratory\Study\Computer Vision\opencv4-python\333.jpg'
img1 = cv.imread(path)
e1 = cv.getTickCount()
for i in range(5,49,2):
img1 = cv.medianBlur(img1,i)#中值滤波
e2 = cv.getTickCount()
t = (e2 - e1)/cv.getTickFrequency()
print(t)
OpenCV中的默认优化 许多 OpenCV 函数都是使用 SSE2、 AVX 等进行优化的。 它还包含未优化的代码。因此,如果我们的系统支持这些特性,我们就应该利用它们(几乎所有现代的处理器都支持它们)。在编译时默认启用它。因此,如果启用了 OpenCV,它将运行优化的代码,否则它将运行未优化的代码。你可以使用 cvUseoptimized 检查是否启用 / 禁用和 cvSetuseoptimized 以启用 / 禁用它。让我们看一个简单的例子。
cv.useOptimized()timeit res = cv.medianBlur(img,49)#关闭它
cv.setUseOptimized(False)
cv.useOptimized()timeit res = cv.medianBlur(img,49)
在IPython中衡量性能 有时你可能需要比较两个类似操作的性能。IPython为你提供了一个神奇的命令计时器来执行此操作。它会多次运行代码以获得更准确的结果。同样,它们适用于测量单行代码。
例如,你知道以下哪个加法运算更好,x = 5; y = x**2, x = 5; y = xx, x = np.uint8([5]); y = xx或y = np.square(x)?我们将在IPython shell中使用timeit得到答案。
In [10]: x = 5In [11]: %测时 y=x**2
10000000 loops, best of 3: 73 ns per loopIn [12]: %测时 y=x*x
10000000 loops, best of 3: 58.3 ns per loopIn [15]: z = np.uint8([5])In [17]: %测时 y=z*z
1000000 loops, best of 3: 1.25 us per loopIn [19]: %测时 y=np.square(z)
1000000 loops, best of 3: 1.16 us per loop
我们将再尝试一个示例。这次,我们将比较cv.countNonZero和np.count_nonzero对于同一张图片的性能。
In [35]: %测时 z = cv.countNonZero(img)
100000 loops, best of 3: 15.8 us per loop
In [36]: %测时 z = np.count_nonzero(img)
1000 loops, best of 3: 370 us per loop
看,OpenCV 函数比 Numpy 函数快近25倍。
注意 通常,OpenCV函数比Numpy函数要快。因此,对于相同的操作,首选OpenCV功能。但是,可能会有例外,尤其是当Numpy处理视图而不是副本时。
性能优化技术 有几种技术和编码方法可以充分利用 Python 和 Numpy 的最大性能。这里只注明相关信息,并提供重要信息来源的链接。这里要注意的主要事情是,首先尝试以一种简单的方式实现算法。一旦它运行起来,分析它,找到瓶颈并优化它们。
- 尽量避免在Python中使用循环,尤其是双/三重循环等。它们本来就很慢。
- 由于Numpy和OpenCV已针对向量运算进行了优化,因此将算法/代码向量化到最大程度。
- 利用缓存一致性。
- 除非需要,否则切勿创建数组的副本。尝试改用视图。数组复制是一项昂贵的操作.
即使执行了所有这些操作后,如果你的代码仍然很慢,或者不可避免地需要使用大循环,请使用Cython等其他库来使其更快。
2.Scipy讲义- 高级Numpy:http://scipy-lectures.github.io/advanced/advanced_numpy/index.html#advanced-numpy
3.IPython中的时序和性能分析:http://pynash.org/2013/03/06/timing-and-profiling/
推荐阅读
- opencv|图像处理之椒盐噪声的添加与去除
- OpenCV|【OpenCV 完整例程】89. 带阻滤波器的传递函数
- OpenCV|【OpenCV 完整例程】90. 频率域陷波滤波器
- OpenCV|【OpenCV 完整例程】22. 图像添加非中文文字
- OpenCV|【OpenCV 完整例程】91. 高斯噪声、瑞利噪声、爱尔兰噪声
- 灰度世界算法(Gray World Algorithm)和White Patch Retinex算法
- 安卓开发|通过RenderScript 实现 NV21转Bitmap、两张Bitmap按照透明度混合的工具类
- 基于SLIC的细胞分割与检测
- 科学计算|超像素分割
- MFC|gdal 图像金字塔