假设我有一个索引为0..n-1的数组。有没有办法选择每个线程将处理哪些单元格?例如线程0将处理单元格0和5,线程1将处理单元格1和6,依此类推。
当前,每个线程操作的单元的选择不是由我决定的,而是系统选择的。我想得到那个控制权。
答案 0 :(得分:1)
使用带有默认参数的!$OMP PARALLEL DO
时,工作将在线程之间平均共享。如果您有10个线程和1000次迭代,则线程0将在1..100上运行,线程1将在101..200上运行,依此类推。
如果您想要更好的控件,请不要使用PARALLEL DO
。仅使用将在所有线程中运行相同代码的$! OMP PARALLEL
。在您的代码调用OMP_get_thread_num
中,它将返回当前线程的ID。然后,您可以测试该值并将其分配给线程i
,以进行所需的任何工作。例如,您可以计算该线程应处理的单元格范围。给出线程总数的OMP_get_num_threads
也很有用。
例如,对于静态计划,C中omp parallel for
个元素上的n
绝对等于
#pragma omp parallel
{
int id_thread=omp_get_thread_num();
int num_threads=omp_get_num_threads();
int min_index=id_thread*(n/num_threads);
int max_index=min((id_thread+1)*(n/num_threads),n)-1;
for(int i=min_index; i<= max_index; i++){
// whatever
}
}
对于fortran中的OMP PARALLEL DO
来说是相同的(但是我对C语法有更好的了解)。如果要处理给定线程上的特定元素,则可以在给定线程中要考虑的索引范围上进行更复杂的计算。因此,如果您要处理每个num_threads
元素(示例中为5),则可以执行以下操作:
#pragma omp parallel
{
int id_thread=omp_get_thread_num();
int num_threads=omp_get_num_threads();
for(int i=id_thread; i<n; i+=num_threads){
// whatever
}
}
如果num_threads
= 5,线程0将处理元素0、5,...,线程1元素1、6,依此类推。 Fortran翻译应该很简单。