关闭

CUDA之窄带常规波束形成

521人阅读 评论(0) 收藏 举报
分类:

思路

现在手上有了cuda的复数矩阵乘法和复数矩阵转置。理论上讲可以做一个简单的波束形成了。
按照matlab之并行计算 的思想把for循环都变成矩阵来做。

  • 复数矩阵定义
typedef struct {
    int width;
    int height;
    int stride;
    double * real;
    double * imag;
} Matrix;
  • 复数矩阵乘法
CvalueR += AsR[row][e] * BsR[e][col]-AsI[row][e]*BsI[e][col];
CvalueI += AsR[row][e] * BsI[e][col]+AsI[row][e]*BsR[e][col];
  • 复数共轭转置
B.real[j + i*B.stride] = A.real[i + j*A.stride];
B.imag[j + i*B.stride] = -A.imag[i + j*A.stride];
  • 阵列流形矢量a的表示
a = exp(-jay*2*pi*sin(theta'*pi/180)*[0:N-1]*f0*d/c);

由于没有C里面没有复数计算。将a表示为两部分:

a.real = cos(-2*PI*j*f0*d/c*sin(theta*PI/180)); 
a.imag = sin(-2*PI*j*f0*d/c*sin(theta*PI/180));

同时可以看作是两次矩阵乘法。

    Matrix tempN,temptheta,tempA;
    init(&tempN,1,M);
    init(&temptheta,N_THETA,1);
    init(&tempA,N_THETA,M);

    int  theta = -90; //起始扫描角

    for(i = 0; i<M; i++)
    {
        tempN.real[i] = -2*PI*i*f0*d/c;
    }
    for(i=0;i<N_THETA;i++)
    {
        temptheta.real[i] = sin(theta*PI/180);
        theta = theta + 1;
    }
    CMatMul(temptheta,tempN,tempA) ;
    for(i=0; i<A.height*A.width; i++)
    {
        A.real[i] = cos(tempA.real[i]);
        A.imag[i] = sin(tempA.real[i]);
    }
  • 求对角
    这个就完全是数字问题了,很简单。
    for(i=0;i<N_THETA;i++)
    {
        BeamDOA.real[i] = tempbeam.real[(N_THETA+1)*i];
        BeamDOA.imag[i] = tempbeam.imag[(N_THETA+1)*i];
    }

问题

  • hilbert只能输入SIZE为2的N次方的信号。不然就会有死循环啦
  • matlab中的data’是data的共轭转置矩阵。因此在我的矩阵转置中应设置虚部求负
  • 计算A时的矩阵乘法的两个因子的宽度 比第一次求R时的矩阵乘法的TILE_SIZE 小,所以求出来A值都为零。对于同一个矩阵乘法函数,由于计算不同乘法时的矩阵宽度不同,应设置不同大小的TILE_SIZE。

结果

DATASIZE BLOCKSIZE TIME
2^15 1 1.332s
2^15 2 0.968s
2^15 4 0.509s
2^15 8 0.366s

由于上不了图,只能口述了,DOA数据与matlab计算的数据对比一致。
成功啦~!蛮开心的~!

然后我就发现直接用CPU只需要0.19s又被吊打了…

0
0

查看评论
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场
    个人资料
    • 访问:12856次
    • 积分:306
    • 等级:
    • 排名:千里之外
    • 原创:18篇
    • 转载:1篇
    • 译文:0篇
    • 评论:1条
    文章分类
    最新评论