Могу ли я назначить несколько потоков для раздела кода в OpenMP? - PullRequest
6 голосов
/ 06 сентября 2011

Я ищу способ выполнять разделы кода параллельно, используя несколько потоков для каждого раздела. Например, если у меня 16 потоков и две задачи, я хочу, чтобы 8 потоков каждый выполнял эти две задачи одновременно. OpenMP имеет несколько конструкций (section, task), которые выполняют общий код параллельно, но они являются однопоточными. В моем сценарии использование section или task приведет к тому, что один поток выполнит каждую из двух задач, а 14 потоков будут бездействовать.

Возможно ли что-то подобное с OpenMP? Если да, то как мне это сделать, а если нет, что я могу использовать для этой цели?

Спасибо за ваше время!

изменить 2:

Позвольте мне расширить этот вопрос с примером кода:

class some_class{
    void task(){
        cout<<"Entering the task method"<<endl;
        #pragma openmp parallel for
            for(int i=0; i < large_matrix.rows(); i++){
                 perform_thread_safe_operation(large_matrix.getRow(i));
            }
    }

    matrix large_matrix;
};


void main(){
    //I have 16 cores, so I want to spawn 16 threads
     some_class o1;
     some_class o2;
    // I want 8 of the 16 threads to execute this line:
    o1.task();
    // and 8 remaining threads to execute this line:
    o2.task();
}

1 Ответ

10 голосов
/ 06 сентября 2011

Вы можете сделать это, используя вложенные параллельные области.

omp_set_nested(1);

#pragma omp parallel num_threads(2)
{
    if (omp_get_thread_num() == 0){
#pragma omp parallel num_threads(8)
        {

            //  Task 0

        }
    }else{
#pragma omp parallel num_threads(8)
        {

            //  Task 1

        }
    }
}

В качестве альтернативы, вы можете сделать это так:

#pragma omp parallel num_threads(16)
{
    if (omp_get_thread_num() < 8){
        //  Task 0
    }else{
        //  Task 1
    }
}

Обратите внимание, этот код не будет работать, если OpenMP решитиспользовать менее 16 потоков.Для этого вам нужно будет ввести собственный код очистки.

РЕДАКТИРОВАТЬ: В ответ на ваше обновление:

class some_class{
    void task(){
        cout<<"Entering the task method"<<endl;

#pragma omp parallel for num_threads(8)
        for(int i=0; i < large_matrix.rows(); i++){
            perform_thread_safe_operation(large_matrix.getRow(i));
        }
    }

    matrix large_matrix;
};


void main(){

    omp_set_nested(1);

    //I have 16 cores, so I want to spawn 16 threads
     some_class o1;
     some_class o2;

#pragma omp parallel num_threads(2)
   {
       if (omp_get_thread_num() == 0){
           // I want 8 of the 16 threads to execute this line:
           o1.task();
       }else{
           // and 8 remaining threads to execute this line:
           o2.task();
       }
   }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...