【问题标题】:cuBLAS Dgemm product with pythoncuBLAS Dgemm 产品与 python
【发布时间】:2016-02-19 13:17:03
【问题描述】:

我有2 简单矩阵AB,我正在计算它们的乘法。 数组看起来像这样(使用numpy 作为模型)

A=np.array(([1,2,3],[4,5,6])).astype(np.float64)
B=np.array(([7,8],[9,10],[11,12])).astype(np.float64)

这是矩阵的形状

A: (2, 3)

B: (3, 2)

现在,我正在尝试使用cublasDgemmBatched 来获取产品。

我对应用 cublasDgemmBatched 时的 m,nk 值应该是什么感到困惑。 另外,我不确定数组的前导维度(ldaldbldc)是什么。

这里有一个nice 3d example,但我似乎无法让这个函数在二维矩阵上工作。

理想情况下,我希望得到与np.dot 相同的结果。

【问题讨论】:

  • 这可能是因为批处理 gemm 用于二维矩阵(或您所说的三维矩阵)的数组。如果您真的坚持将 gemmbatched 用于二维数组,那么以您的示例为例:m = 2, n = 2, k = 3, lda = 3, ldb = 2, ldc = 2。虽然我不能自信地说这是否会奏效。或者,参考您链接到的示例,只需设置l=1
  • 您可能希望更明确地了解 2 个矩阵的点积是什么意思。 matlab 的definition 表示一组矩阵列的点积。这意味着矩阵将具有相同的形状。如果您确实想要一组矩阵列的单独点积,那么使用批处理 gemm 可能不是可行的方法,因为它相当 compilicated to set up 并且我认为使用矩阵乘积作为向量点积是矫枉过正
  • 我想得到和 np.dot() 一样的结果
  • 那么你可能想使用cublasDgemm。调整 3D 示例以适合您的 2D 示例可能如下所示 cublasDgemm(self.cublas_handle, 'n','n', 2, 2, 3, alpha, b_arr.gpudata, 2, a_arr.gpudata, 3, beta, c_arr.gpudata, 2)
  • 谢谢。我想将您的回复标记为答案,但我不确定如何。

标签: python matrix cuda pycuda cublas


【解决方案1】:

我没有 skcuda.blas 来确认这一点。但是一个更完整的例子可能看起来像

A = np.array(([1, 2, 3], [4, 5, 6])).astype(np.float64)
B = np.array(([7, 8], [9, 10], [11, 12])).astype(np.float64)

m, k = A.shape
k, n = B.shape

a_gpu = gpuarray.to_gpu(A)
b_gpu = gpuarray.to_gpu(B)
c_gpu = gpuarray.empty((m, n), np.float64)

alpha = np.float64(1.0)
beta = np.float64(0.0)

a_arr = bptrs(a_gpu)
b_arr = bptrs(b_gpu)
c_arr = bptrs(c_gpu)

cublas_handle = cublas.cublasCreate()

cublas.cublasDgemm(cublas_handle, 'n','n',
                   n, m, k, alpha,
                   b_arr.gpudata, m,
                   a_arr.gpudata, k,
                   beta, c_arr.gpudata, m)

【讨论】:

    【解决方案2】:

    模仿np.dot() 的一个非常简单的方法是使用culinalg.dot(),它在后面使用cuBLAS,参见skcuda.linalg.dot。下面,一个简单的例子:

    import pycuda.autoinit
    import pycuda.gpuarray as gpuarray
    import pycuda.driver as drv
    import numpy as np
    
    import skcuda.linalg as culinalg
    import skcuda.misc as cumisc
    culinalg.init()
    
    A = np.array(([1, 2, 3], [4, 5, 6])).astype(np.float64)
    B = np.array(([7, 8, 1, 5], [9, 10, 0, 9], [11, 12, 5, 5])).astype(np.float64)
    
    A_gpu = gpuarray.to_gpu(A)
    B_gpu = gpuarray.to_gpu(B)
    
    C_gpu = culinalg.dot(A_gpu, B_gpu)
    
    print(np.dot(A, B))
    print(C_gpu)
    

    【讨论】:

      猜你喜欢
      • 2016-10-09
      • 2012-02-01
      • 2015-04-24
      • 2017-03-12
      • 1970-01-01
      • 2015-08-29
      • 1970-01-01
      • 2014-11-08
      • 1970-01-01
      相关资源
      最近更新 更多