我是OpenMP Programming的新手,我在GCC上执行了几个open-mp示例程序。我想知道如何决定启动多少线程(即如何决定omp_set_num_threads()函数的参数)以在双核intel处理器上获得更好的性能。
* 这是我的示例程序 *
#include<math.h>
#include<omp.h>
#include<stdio.h>
#include<time.h>
#define CHUNKSIZE 10
#define N 100000
#define num_t 10
void main ()
{
int runTime;
int i, chunk;
int a[N], b[N], c[N],threads[num_t];
int thread_one=0,thread_two=0;
clock_t start,end;
omp_set_num_threads(num_t);
/* Some initializations */
for (i=0; i < N; i++)
a[i] = b[i] = i + 2.0;
chunk = CHUNKSIZE;
#pragma omp parallel shared(a,b,c,chunk,threads) private(i)
{
#pragma omp for schedule(dynamic,chunk)
for (i=0; i < N; i++)
{
c[i] = pow((a[i] * b[i]),10);
threads[omp_get_thread_num()]++;
}
} /* end of parallel section */
for(i=-1;i<num_t;i++)
printf("Thread no %d : %d\n",i,threads[i]);
}
答案 0 :(得分:3)
根据经验,首先尝试将线程编号设置为机器的核心数。然后尝试减少此数字以查看是否有任何改进。
顺便说一下,设置omp_set_num_threads
环境变量比使用OMP_NUM_THREADS
更方便进行此类测试
答案 1 :(得分:3)
我的建议:不要打扰。如果它是一个计算密集型应用程序(openmp主要用于这里,你有什么),那么图书馆本身就可以很好地管理所有内容。
答案 2 :(得分:0)
最佳线程数取决于许多参数,很难设计出一般的经验法则。
对于具有低读取/计算比率的计算密集型任务,最好将线程数设置为等于CPU核心数。
对于大量内存绑定任务,在线程数等于内核数之前,增加线程数可能会使内存带宽饱和。循环矢量化可以显着影响单个线程的内存带宽。在某些情况下,线程在CPU缓存中共享大量数据,但在某些情况下 - 它们不会,并且增加它们的数量会减少可用的缓存空间。此外,NUMA系统通常提供比SMP系统更好的带宽。
在某些情况下,使用比核心更多的线程可以实现最佳性能 - 在每个任务中观察到大量阻塞等待时都是如此。有时SMT或超线程可以隐藏内存延迟,有时它不能,具体取决于正在执行的内存访问类型。
除非您可以对代码性能进行建模并对要运行的最佳线程数进行有根据的猜测,否则只需尝试多个值。