在cuBLAS howto中转置矩阵乘法

时间:2013-01-30 02:34:50

标签: cuda matrix-multiplication transpose blas cublas

问题很简单:我有两个矩阵A和B,它们是M乘N,其中M>> N.我想首先采用A的转置,然后将其乘以B(A ^ T * B)将其放入C中,即N乘N.我已为A和B设置了所有内容,但是如何做我没有给出错误的答案而正确调用了cublasSgemm?

据我所知,cuBlas有一个cublasOperation_t enum用于预先转置事物,但不知怎的,我还没有正确使用它。我的矩阵A和B按行主顺序排列,即[row1] [row2] [row3] .....在设备存储器中。这意味着A被解释为A-transposed,BLAS需要知道我的A是按列主顺序。我目前的代码如下所示:

float *A, *B, *C;
// initialize A, B, C as device arrays, fill them with values
// initialize m = num_row_A, n = num_row_B, and k = num_col_A;
// set lda = m, ldb = k, ldc = m;
// alpha = 1, beta = 0;
// set up cuBlas handle ...

cublasSgemm(handle, CUBLAS_OP_T, CUBLAS_OP_N, m, n, k, &alpha, A, lda, B, ldb, &beta, C, ldc);

我的问题:

我是否正确设置了m,k,n?

lda,ldb,ldc怎么样?

谢谢!

1 个答案:

答案 0 :(得分:12)

因为cuBLAS总是假设矩阵存储在列主要中。您可以使用cublas_geam()

将矩阵首先转换为colum-major

您可以将存储在行主中的矩阵A视为存储在column-major中的新矩阵AT。矩阵AT实际上是A的转置。对于B做同样的事情。然后,您可以通过C=AT * BT^T

计算存储在列专业中的矩阵C.
float* AT = A;
float* BT = B;

主要维度是与存储相关的参数,无论您是否使用转置标记CUBLAS_OP_T,它都不会更改。

lda = num_col_A = num_row_AT = N;
ldb = num_col_B = num_row_BT = N;
ldc = num_row_C = N;
cuBLAS GEMM例程中的

mn是结果矩阵C的#rows和#cols,

m = num_row_C = num_row_AT = num_col_A = N;
n = num_col_C = num_row_BT = num_col_B = N;

k是A ^ T和B的共同维度,

k = num_col_AT = num_row_B = M;

然后你可以通过

调用GEMM例程
cublasSgemm(handle, CUBLAS_OP_N, CUBLAS_OP_T, m, n, k, &alpha, AT, lda, BT, ldb, &beta, C, ldc);

如果您希望矩阵C存储在行主中,您可以使用公式CT = BT * AT^T计算存储在列专业中的CT

cublasSgemm(handle, CUBLAS_OP_N, CUBLAS_OP_T, n, m, k, &alpha, BT, ldb, AT, lda, &beta, CT, ldc);

请注意,您不必交换mn,因为在这种情况下C是方阵。