#pragma omp parallel for schedule(static) default(none)
for(int row = 0; row < m_height; row++)
{
for(int col = 0; col < m_width; col++)
{
int RySqr, RxSqr;
SettingSigmaN(eta, m_RxInitial + col, m_RyInitial + row , RxSqr, RySqr);
FunctionUsing(RySqr,RxSqr);
}
}
void CImagePro::SettingSigmaN(int Eta, int x, int y, int &RxSqr, int &RySqr, int &returnValue)
{
int rSqr = GetRadius(x,y,RxSqr,RySqr);
returnValue = GetNumberFromTable(rsqr);
}
int CImagePro::GetRadius(int x, int y, int &RxSqr, int &RySqr)
{
if (x == m_RxInitial)
{
RxSqr = m_RxSqrInitial;
if (y == m_RyInitial)
{
RySqr = m_RySqrInitial;
}
else if ( abs(y) % 2 == abs(m_RyInitial) % 2)
{
RySqr = RySqr + (y<<2) + 4; //(y+2)^2
}
}
else
{
RxSqr = RxSqr + ( x << 1) + 1; //(x+1)^2
}
return clamp(((RxSqr+RySqr)>>RAD_RES_REDUCTION),0,(1<<(RAD_RES-RAD_RES_REDUCTION))-1);
}
好,所以这是我的代码,我的问题在GetRadius函数内。 因为我有很多线程,每个线程都在x,y的不同位置开始。但是我真的不明白GetRadius()里面的错误在哪里。
我想也许是RySqr计算。你能建议一种调试方法吗?或者你能看出我的问题吗?
更新:
这修复了我的大部分代码: 我还是不太懂,为什么不同线程之间会有跳跃。
int CImagePro::GetRadius(int x, int y, int &RxSqr, int &RySqr)
{
if (x == m_RxInitial)
{
RxSqr = m_RxSqrInitial;
}
else
{
RxSqr = x * x;
}
if (y == m_RyInitial)
{
RySqr = m_RySqrInitial;
}
else if (abs(y) % 2 == abs(m_RyInitial) % 2)
{
RySqr = y * y;
}
return clamp(( (RxSqr + RySqr) >> RAD_RES_REDUCTION), 0, ( 1 << (RAD_RES - RAD_RES_REDUCTION) ) - 1);
}
答案 0 :(得分:1)
我真的很想知道这件事是否汇编了?您指定default(none)
,但始终使用您班级的数据成员。它们都是静态的吗?
你可以做的是i)离开default(none)
,这意味着default(shared)
,ii)通过明确地共享它们来共享访问值,或者iii)初始化你在里面使用的变量并行区域,以便每个线程拥有它自己的私有副本,比如m_RxInitial
,称为p_RxInitial
等。第一个选项几乎可以保证让您陷入麻烦。
以下说明选项ii):
1)制作一个包含你需要传递的所有东西的助手类,对你来说可能是
struct ShareData{
int s_RxInitial
/* ... */
}
2)在包含并行部分的成员函数中,在并行循环定义
之前ShareData SD;
SD.s_RxInitial = m_RxInitial;
/* ... */
3)将其交给平行部分
#pragma omp parallel for schedule(static), default(none), shared(SD)
4)在函数调用中使用SD数据库。
我希望这很清楚。如果有人提供更优雅的解决方案,我将不胜感激。
如果您想要选项iii)的私有变量,则可以说firstprivate(SD)
而不是shared(SD)
。这将使每个线程初始化(到原始值)SD的私有副本。通过避免串行访问,它可能会或可能不会提供一些性能优势。几天前我遇到了类似的问题,并没有什么区别。
答案 1 :(得分:-2)
如果你需要保证像你一样制作if语句,或者根本不进行并行化,因为它是一个关键部分,你不能保证线程执行的顺序。