As already answered by Massimiliano, the easiest way to achieve what you want is to use the sections
construct:
#pragma omp parallel sections
{
#pragma omp section
Func1();
#pragma omp section
Func2();
#pragma omp section
Func3();
}
(when the sections
construct is the only thing nested inside a parallel
region, both pragmas can be combined as shown)
Each section
scopes the statement or block immediately following it. E.g. if you'd like to include some more code in a section, you should put it inside a block:
#pragma omp section
{
Func1();
SomeOtherFunc1();
}
A more general way to control what each thread does is to examine the thread ID as returned by omp_get_thread_num()
and to branch in accordance. This resembles the way MPI programs are written:
#pragma omp parallel
{
switch (omp_get_thread_num())
{
case 0:
Func1();
break;
case 1:
Func2();
break;
case 2:
Func3();
break;
default:
// Do nothing
}
}
One obvious disadvantage is that it would only work unless there are at least 3 threads in the team that executes the parallel region, i.e. code that relies on thread IDs becomes somewhat non-portable. In contrast, the sections
directive works with any number of threads, e.g. if there is only one thread, all sections would be executed sequentially.