Я пишу программу на C ++ с научными целями. Программа работает хорошо и дает хорошие результаты, поэтому я решил улучшить его производительность с помощью OpenMP. Цикл, который я хочу оптимизировать, следующий:
//== #pragma omp parallel for private(i,j)
for (k=0; k < number; k++)
{
for (i=0; i < L; i++)
{
for (j=0; j < L; j++)
{
red[i][j] = UNDEFINED;
}
}Point inicial = {L/2, L/2, OCCUPIED};
red[L/2][L/2] = OCCUPIED;
addToList(inicial, red, list, L,f);
oc.push_back(inicial);
while (list.size() > 0 && L > 0)
{
punto = selectPoint(red, list, generator, prob, p);
if (punto.state == OCCUPIED)
{
addToList(punto, red, list, L,f);
oc.push_back(punto);
}
else
{
out.push_back(punto);
}}
L = auxL;
oc.clear();
out.clear();
list.clear();
}
f = f*1.0/(number*1.0);
if (f > 0.5)
{
inta = inta;
intb = p;
p = (inta + intb) / 2.0;
}
else if (f < 0.5)
{
intb = intb;
inta = p;
p = (inta + intb) / 2.0;
}
cout << p << endl;}
Моя попытка с OpenMP прокомментирована выше. Как вы видете Я объявил i
а также j
как частный потому что они объявлены перед параллельным разделом. Я также пытался сделать L
частный, без результатов. Только ошибки сегментации и плохие указатели повсюду.
Я думаю, что проблема заключается в том, что цикл внутри вложен. Мои вопросы: Это omp parallel for
правильно в этом случае? или я должен попытаться оптимизировать только этот цикл while? Являются ли std::vector
мешает OpenMP?
НОТА: list
, oc
а также out
являются std::vector<Point>
, а также Point
простая структура с тремя свойствами int addToList
это функция без петель внутри.
Возможно, вы захотите пройти учебник OpenMP. Когда вы смотрите на код OpenMP, вам нужно представить, что может происходить параллельно. принимать
oc.push_back(inicial);
Могут ли два потока попытаться сделать это одновременно? Да. Есть ли std::vector
поддерживать параллелизм? Нет.
Код выше полон этих вещей.
Если вы хотите использовать структуры данных в вашей OpenMP-оде, вам нужно использовать замки. Исходя из моего личного опыта, когда это происходит, гораздо лучше реорганизовать алгоритм, чем использовать его. Хотя OpenMP + блокировки возможны, обычно это указывает на проблему с идеей (= возможно субъективное представление).
Текущий ответ указывает на параллелизм в коде, но обратите внимание, что не все структуры данных должны быть реализованы с блокировками для достижения безопасности потока. Это также lock-free
структуры данных. Для этого конкретного случая мы могли бы заблокировать свободный связанный список Харриса: https://timharris.uk/papers/2001-disc.pdf
Несмотря на то, что я знаю, что указание на проблемы параллелизма для OP очень помогает в этой точке, я хочу убедиться, что мы не передадим неверное сообщение, сказав, что блокировки абсолютно необходимы для обеспечения безопасности потоков.