0

我有这段 C++ 代码,我想将它移植到 CUDA。

for (int im = 0; im < numImages; im++)
{
    for (p = 0; p < xsize*ysize; p++) 
    {
        bool ok = false;

        for (f = 0; f < numFeatures; f++)
        {
            if (feature[im][f][p] != 0) 
            {
                ok = true;
                break;
            }
        }
        if (ok)
        {         
            minDist = 1e9;
            for (i = 0; i < numBins; i++) 
            {
                dist = 0;
                for (f = 0; f < numFeatures; f++)
                {
                    dist += (float)((feature[im][f][p]-clusterPoint[f][i])*(feature[im][f][p]-clusterPoint[f][i]));
                }

                if (dist < minDist) 
                {
                    minDist = dist;
                    tmp = i;          
                }
            }//end for i  

            for (f = 0; f < numFeatures; f++) 
                csum[f][tmp] += feature[im][f][p];

            ccount[tmp]++;

            averageDist[tmp] += sqrt(minDist);

        } // end if (ok)
    }  //end for p    
}// end for im

我想计算csum,ccountaverageDist在 GPU 中。csum并且averagedist是浮点数,ccount是整数。

这是一个并行减少问题吗?

4

2 回答 2

1

numBins我没有完全理解你的代码应该做什么,我也不知道和的近似值是什么numFeatures。尽管如此,我会并行这个循环:for (p = 0; p < xsize*ysize; p++),以便每个线程计算它的值并将它们存储在全局数组中。拥有可以计算的这些特征距离数组csumccountaverageDist使用标准的并行缩减。

可以通过重复启动内核来计算图像 的主循环,for (int im = 0; im < numImages; im++)也可以通过像素循环使其一次并行。

if(ok)不够频繁的情况下,会发生翘曲发散(请参阅this)。避免这种情况,您不能为每个像素分配一个线程,只能分配一个扭曲,并将剩余的计算分配给该扭曲内的线程。

于 2013-01-28T14:52:16.793 回答
0

是的,您可以使用 CUDA 进行求和。但是,元素的数量应该足够大,使得在 GPU 上求和所用的时间应该小于在 CPU 上求和所用的时间。这可能会帮助你

于 2013-01-28T14:27:14.560 回答