Algorithm TERCOM算法-在CUDA中从单线程更改为多线程

Algorithm TERCOM算法-在CUDA中从单线程更改为多线程,algorithm,cuda,navigation,Algorithm,Cuda,Navigation,我目前正在将一个线程从只使用一个线程移植到使用多个线程。简要说明,TERCOM算法接收5个测量值和标题,并将这些测量值与预存储的地图进行比较。算法将选择最佳匹配,即最低平均绝对差(MAD),并返回位置 代码在一个线程和for循环中工作得很好,但是当我尝试使用多个线程和块时,它返回了错误的答案。多线程版本似乎不像单线程版本那样“运行”计算。有人知道我做错了什么吗 下面是用于循环的代码 __global__ void kernel (int m, int n, int h, int N, float

我目前正在将一个线程从只使用一个线程移植到使用多个线程。简要说明,TERCOM算法接收5个测量值和标题,并将这些测量值与预存储的地图进行比较。算法将选择最佳匹配,即最低平均绝对差(MAD),并返回位置

代码在一个线程和for循环中工作得很好,但是当我尝试使用多个线程和块时,它返回了错误的答案。多线程版本似乎不像单线程版本那样“运行”计算。有人知道我做错了什么吗

下面是用于循环的代码

__global__ void kernel (int m, int n, int h, int N, float *f, float heading, float *measurements) 
{
    //Without threads
    float pos[2]={0};
    float theta=heading*(PI/180);
    float MAD=0;

    // Calculate how much to move in x and y direction
    float offset_x = h*cos(theta);
    float offset_y = -h*sin(theta); 

    float min=100000; //Some High value

    //Calculate Mean Absolute Difference
    for(float row=0;row<m;row++)
    {
        for(float col=0;col<n;col++)
        {
            for(float g=0; g<N; g++)
            {
                f[(int)g] = tex2D (tex, col+(g-2)*offset_x+0.5f, row+(g-2)*offset_y+0.5f);
                MAD += abs(measurements[(int)g]-f[(int)g]);
            }
            if(MAD<min) 
            {
                min=MAD;
                pos[0]=col;
                pos[1]=row;
            }
            MAD=0;                  //Reset MAD
        }
    }

    f[0]=min;
    f[1]=pos[0];
    f[2]=pos[1];
}
\uuuu全局\uuuuu无效内核(int m、int n、int h、int n、float*f、float heading、float*measurements)
{
//无螺纹
float pos[2]={0};
浮动θ=航向*(PI/180);
float-MAD=0;
//计算在x和y方向上移动的量
浮动偏移量x=h*cos(θ);
浮动偏移量y=-h*sin(θ);
float min=100000;//某个高值
//计算平均绝对差

对于(float row=0;row这里的基本问题是代码中有一个内存竞争,其核心是将
f
用作某种线程本地暂存空间和输出变量。每个并发线程都将同时尝试将值写入
f
中的相同位置,这将产生未定义的行为嗯

据我所知,将
f
用作暂存空间根本就不是必需的,内核的主要计算部分可以写成如下内容:

if(idx < n && idy < m)
{
    for(float g=0; g<N; g++)
    {
        float fval = tex2D (tex, idx+(g-2)*offset_x+0.5f, idy+(g-2)*offset_y+0.5f);
        MAD += abs(measurements[(int)g]-fval); 
    }
    min=MAD;
    pos[0]=idx;
    pos[1]=idy;
}
if(idx对于(float g=0;gMAD在已初始化的MAD和pos代码段中均未初始化,但未更改任何内容:(使用初始化编辑代码您希望从内核得到什么实际结果?它只是
min
pos
还是
f
中的其他值也是必需的?有趣的是,只有min和pos。我使用f变量返回min和pos,而不是使用自己的变量返回值esI在这个问题上已经工作了几天了,但我无法让它工作。我试图打印每个线程的值,你是对的Talonmes。每个线程都有自己的值。所以我的问题是:我是否可以访问一个线程存储的值并将该值放入数组中?换句话说,我需要所有线程的值合二为一array@user2594166:如果你有一个新问题,我建议你在新问题中提问,而不是在评论中。我不会改变我已有的答案,其他人也不知道看这里。不过,他们会看到一个新问题
dim3 dimBlock( 16,16 );
dim3 dimGrid;
dimGrid.x = (n + dimBlock.x - 1)/dimBlock.x;
dimGrid.y = (m + dimBlock.y - 1)/dimBlock.y;

kernel <<< dimGrid,dimBlock >>> (m, n, h, N, dev_results, heading, dev_measurements);
if(idx < n && idy < m)
{
    for(float g=0; g<N; g++)
    {
        float fval = tex2D (tex, idx+(g-2)*offset_x+0.5f, idy+(g-2)*offset_y+0.5f);
        MAD += abs(measurements[(int)g]-fval); 
    }
    min=MAD;
    pos[0]=idx;
    pos[1]=idy;
}