英文链接:How to use the OpenCV parallel_for_ to parallelize your code
文章目录
- 目的
- 先决条件
- 简单的示例:绘制曼德尔布罗特集(Mandelbrot set)
- 原理
- 伪代码
目的
本教程的目的是向您展示如何使用OpenCV parallel_for_
框架轻松地并行化代码。为了说明这个概念,我们将编写一个程序来利用几乎所有可用的CPU负载绘制曼德尔布罗特集。完整的教程代码在这里。如果你想要更多关于多线程的信息,你将不得不参考参考书或课程,因为本教程的目的是保持简单。
先决条件
第一个先决条件是用并行框架构建OpenCV。在OpenCV 3.2中,以下并行框架是按顺序提供的:
- Intel线程构建块(应该显式启用第三方库)
- C=并行C/ c++编程语言扩展(应显式启用第三方库)
- OpenMP(集成到编译器中,应该显式启用)
- 苹果GCD(系统范围,自动使用(仅限苹果))
- Windows RT并发性(系统范围,自动使用(仅适用于Windows RT))
- Windows并发(运行时的一部分,自动使用(仅Windows - MSVC++ >= 10))
- Pthreads(如果可用)
如您所见,OpenCV库能使用几个并行框架。一些并行库是第三方库,必须显式地构建和启用CMake(例如TBB, C =),其他的则自动可用(例如APPLE GCD),但是,您应该能够直接访问并行框架,或者通过在CMake和rebuild库中启用选项来实现。
第二个(弱)先决条件与你想要完成的任务有关,因为并不是所有的计算都适合/可以被设置为并行运行。为了保持简单,可以拆分为多个基本操作、没有内存依赖关系(没有可能的竞争条件)的任务可以轻松地并行。计算机视觉处理通常是容易并行的,因为大多数时候一个像素的处理不依赖于其他像素的状态。
简单的示例:绘制曼德尔布罗特集(Mandelbrot set)
我们将使用绘制曼德尔布罗特集的示例来展示如何从规则的顺序代码中轻松地修改代码来并行化计算。
原理
Mandelbrot集合定义被数学家Adrien Douady命名为向数学家Benoit Mandelbrot致敬。它在数学领域之外很出名,因为图像表示是一类分形的一个例子,它是一个数学集合,在每个尺度上都显示出一个重复的模式(甚至,曼德尔布罗特集是自相似的,因为整个形状可以在不同的尺度上重复出现)。要获得更深入的介绍,可以查看相应的Wikipedia文章。这里,我们将介绍绘制Mandelbrot集的公式(来自Wikipedia文章)。
Mandelbrot集合是二次映射迭代下轨道为0的复平面上
c
c
c的值的集合
{
z
0
=
0
z
n
+
1
=
z
n
2
+
c
\begin{cases} z_0 = 0 \\ z_{n+1} = z_n^2 + c \end{cases}
{z0=0zn+1=zn2+c
仍然是有界的。也就是说,当从
z
0
=
0
z_0=0
z0=0开始并重复应用迭代时,无论
n
n
n多大,
z
n
z_n
zn的绝对值都是有界的,则复数
c
c
c是曼德尔布罗特集合的一部分。这也可以表示为
lim sup
n
→
∞
∣
z
n
+
1
∣
⩽
2
\limsup_{n\to\infty}|z_{n+1}|\leqslant2
n→∞limsup∣zn+1∣⩽2
伪代码
生成Mandelbrot集表示的一个简单算法称为“逃逸时间算法”。对于渲染图像中的每个像素,我们使用递归关系测试复数是否在最大迭代次数下有界。不属于Mandelbrot集合的像素将很快转义,而我们假设像素在固定的最大迭代次数之后位于集合中。较高的迭代值将生成更详细的图像,但计算时间将相应增加。我们使用“转义”所需的迭代次数来描述图像中的像素值。
For each pixel (Px, Py) on the screen, do:
{
x0 = scaled x coordinate of pixel (scaled to lie in the Mandelbrot X scale (-2, 1))
y0 = scaled y coordinate of pixel (scaled to lie in the Mandelbrot Y scale (-1, 1))
x = 0.0
y = 0.0
iteration = 0
max_iteration = 1000
while (x*x + y*y < 2*2 AND iteration < max_iteration) {
xtemp = x*x - y*y + x0
y = 2*x*y + y0
x = xtemp
iteration = iteration + 1
}
color = palette[iteration]
plot(Px, Py, color)
}
为了将伪代码与理论联系起来,我们有:
z
=
x
+
i
y
z = x + iy
z=x+iy
z
2
=
x
2
+
i
2
x
y
−
y
2
z^2 = x^2 + i2xy - y^2
z2=x2+i2xy−y2
c
=
x
0
+
i
y
0
c = x_0 + iy_0
c=x0+iy0
在这个图中,我们回想一下复数的实部在x轴上虚部在y轴上。您可以看到,如果我们在特定位置缩放,整个形状可以重复可见。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)