Neo*_*Neo 5 parallel-processing performance openmp
我有两种测量指标的方案,如计算时间和并行加速(sequential_time/parallel_time).
场景1:
顺序时间测量:
startTime=omp_get_wtime();
for loop computation
endTime=omp_get_wtime();
seq_time = endTime-startTime;
Run Code Online (Sandbox Code Playgroud)
并行时间测量:
startTime = omp_get_wtime();
for loop computation (#pragma omp parallel for reduction (+:pi) private (i)
for (blah blah) {
computation;
}
endTime=omp_get_wtime();
paralleltime = endTime-startTime;
speedup = seq_time/paralleltime;
Run Code Online (Sandbox Code Playgroud)
场景2:
顺序时间测量:
for loop{
startTime=omp_get_wtime();
computation;
endTime=omp_get_wtime();
seq_time += endTime-startTime;
}
Run Code Online (Sandbox Code Playgroud)
并行时间测量:
for loop computation (#pragma omp parallel for reduction (+:pi, paralleltime) private (i,startTime,endTime)
for (blah blah) {
startTime=omp_get_wtime();
computation;
endTime=omp_get_wtime();
paralleltime = endTime-startTime;
}
speedup = seq_time/paralleltime;
Run Code Online (Sandbox Code Playgroud)
我知道场景2不是最好的生产代码,但我认为它通过忽略openmp生成和管理(线程上下文切换)几个线程所涉及的开销来衡量实际的理论性能.所以它会给我们一个线性加速.但是场景1考虑了产生和管理线程所涉及的开销.
我的疑问是这样的:在场景1中,我得到一个开始线性的加速,但随着我们移动到更高的迭代次数逐渐减少.在场景2中,无论迭代次数如何,我都会获得完整的线性加速.我被告知,实际上,无论迭代次数如何,场景1都会给我一个线性加速.但我认为它不会因为线程管理导致的高过载.有人可以向我解释为什么我错了吗?
谢谢!对于相当长的帖子感到抱歉.
在很多情况下,方案2也不会给你线性加速 - 线程之间的错误共享(或者,就此而言,真正共享被修改的共享变量),内存带宽争用等.子线性加速通常是真实的,不是测量神器.
更一般地说,一旦你达到了将计时器放入循环的程度,你就会考虑使用更精细的计时信息而不是使用这样的计时器进行测量.您可能希望能够将线程管理开销从实际工作中解脱出来,原因有多种,但是在这里您要尝试通过插入N个额外函数调用来实现omp_get_wtime(),以及算术和减少操作,所有这些操作都会产生不可忽视的开销.
如果你真的想要准确计算computation;在线上花费多少时间,你真的想要使用像采样而不是手动仪器这样的东西(我们在这里谈一下这里的区别).使用gprof或scalasca或openspeedshop(所有免费软件)或英特尔的VTune或其他东西(商业软件包)将为您提供有关在该行上花费多少时间的信息 - 通常甚至通过线程 - 以更低的开销.
首先,通过加速的定义,您应该使用方案1,其中包括并行开销.
在方案2中,测量中的代码错误paralleltime.为了满足方案2中的目标,您需要paralleltime通过分配int paralleltime[NUM_THREADS]和访问它们来获得每个线程omp_get_thread_num()(请注意,此代码将具有错误共享,因此您最好使用填充分配64字节结构).然后,测量每线程计算时间,最后用最长的计算一个不同类型的加速(我说的是一种并行性).
不,你甚至可以看到场景2的亚线性加速,甚至可以获得超线性加速.潜在原因(即排除并行开销)是:
compuation迭代时工作负载长度不同.这将是低速加速的最常见原因(但是,你说负载不平衡并非如此).computation高速缓存和内存成本:当需要大带宽和高工作集时,并行代码可能会受到带宽限制(尽管实际上很少见)和高速缓存冲突.此外,虚假共享是一个重要原因,但很容易避免它.还可以观察到超线性效应,因为使用多核可以具有更多高速缓存(即,私有L1/L2高速缓存).在场景1中,它将包括并行库的开销:
我不认为您的代码(1级静态调度并行循环)由于线程管理而确实具有高并行开销,除非此代码每秒被调用数百万次.所以,可能是我在上面提到的其他原因.
请记住,有许多因素会决定加速; 从固有的并行性(=负载不平衡和同步)到并行库的开销(例如,调度开销).
| 归档时间: |
|
| 查看次数: |
5082 次 |
| 最近记录: |