CUDA中的高斯消除(没有旋转)

时间:2013-11-20 19:15:10

标签: c cuda

我正在尝试使用CUDA解决高斯消除问题。

我有一个N*N矩阵。要获取此矩阵的新元素,我使用下面的CPU代码,其中C.width=N

for(int z=0; z< C.width-1; z++)
{
    for ( int c = z+1 ; c < C.width ; c++ )
    {
        for (int d = z ; d < C.width ; d++ )
        {
            C.elements[c*C.width+d]=C.elements[c*C.width+d] - (B.elements[c*C.width+z]*C.elements[z*C.width+d]);
        }
    }
}

我正在尝试使用CUDA实现它。例如,对于N=512

dim3 dimBlock(16,16,1);

dim3 dimGrid(32,32,1); 

MatMulKernel<<<dimGrid, dimBlock>>>(d_A, d_B, d_C);

我认为对于每次迭代,我应该使用N-i*N个线程来计算元素更新,即

    if(idx>511 || idy>510)
        return;
        for(int i=1; i<512;i++)
        {
            if(idx>=i-1 && idy>=i-1)
                C.elements[(idy+1)*C.width+idx]=C.elements[(idy+1)*C.width+idx]-((C.elements[(idy+1)*C.width+(i-1)]/C.elements[(i-1)*C.width+(i-1)])*C.elements[(i-1)*C.width+idx]);

            __syncthreads();
        }
        }

在GPU和CPU上获得的结果相同,但处理时间为Time(CPU)=2*Time(GPU)

N=512Time(CPU) = 1900 ms; Time(GPU) = 980 ms

N=1024Time(CPU) = 14000 ms;时间(GPU)= 7766毫秒 。 。

我认为加速应该比我现在的速度更快。我的并行代码有什么错误吗?你能帮我解决一下如何重写我的代码吗?

感谢您的帮助!

1 个答案:

答案 0 :(得分:4)

高斯消元可被视为两步程序。第一步旨在将线性系统转换为上三角线性系统,第二步包括求解如此获得的上三角线性系统。第二步在CUDA中是微不足道的,可以由cublasStrsm有效地执行。您在帖子中提到的第一步是棘手的​​部分。

有几种优化方法可以解决第一步。我认为你的做法有些天真,我建议研究文献以达到体面的加速。

基本上,执行原始系统到上三角形的转换可以通过平铺方法来执行,从某些角度来看,它类似于用于执行矩阵的平铺方法 - CUDA C编程指南的经典示例中的矩阵乘法。

平铺方法可以通过特意编写的内核或大量使用cuBLAS例程来执行。

上个月(2013年11月),以下论文

Manuel Carcenac,“从瓦片算法到条带算法:基于CUBLAS的高斯GPU并行实现,用于分辨存储在固态设备阵列上的超大密集线性系统”,超级计算杂志,DOI 10.1007 / s11227-013-1043-3

提出了一种基于cuBLAS使用的平铺/剥离方法。

所有上述方法都在M. Carcenac的网页上以Application: linear system resolution with Gauss method的形式进行了总结。

此外,Gaussian elimination with CUDA帖子提供了可下载的Visual Studio 2010项目,该项目通过一些性能测试实现了所有这些项目。从可用的代码中,您可以针对您感兴趣的体系结构进行自己的测试,并体验M. Carcenac对其他方法的改进。