【发布时间】:2017-07-11 10:56:52
【问题描述】:
我想利用 OpenMP 使我的任务并行化。
我需要对数组的所有元素减去相同的数量,然后将结果写入另一个向量。两个数组都使用malloc 动态分配,第一个数组由文件中的值填充。每个元素的类型为uint64_t。
#pragma omp parallel for
for (uint64_t i = 0; i < size; ++i) {
new_vec[i] = vec[i] - shift;
}
其中shift 是我想从vec 的每个元素中删除的固定值。 size 是 vec 和 new_vec 的长度,大约是 200k。
我在 Arch Linux 上使用 g++ -fopenmp 编译代码。我在 Intel Core i7-6700HQ 上,我使用 8 个线程。当我使用 OpenMP 版本时,运行时间要高 5 到 6 倍。当我运行 OpenMP 版本时,我可以看到所有内核都在工作。
我认为这可能是由虚假共享问题引起的,但我找不到。
【问题讨论】:
-
您的内存带宽有限,因为您尝试进行并行计算很简单,基本上只是在内存位置之间移动数据。添加线程将导致内存缓存未命中/抖动和预取失败。这样做的效果是代码运行速度较慢。现代 PC 上的内存总线大约有 1.5 个线程。
-
@RichardCritten 这不是真的。高端处理器具有设计的带宽上限,因此您需要使用多线程来使它们饱和。查看我的答案中的链接。
-
如何衡量执行时间?
-
@HristoIliev 我使用
perf stat -r200来平均执行时间 -
您能生成一个minimal reproducible example 吗?循环的绝对执行时间是多少秒?这是代码中唯一的 OpenMP 区域吗?它在单个程序运行中执行多少次?这可能是 OpenMP 开销。
标签: c++ c performance openmp false-sharing