用cupy增加内环距离函数

Posted

技术标签:

【中文标题】用cupy增加内环距离函数【英文标题】:Increasing inner loop distance function with cupy 【发布时间】:2018-05-14 14:58:45 【问题描述】:

我试图在迭代内部循环数组时提高给定距离函数的计算速度 - c(x, y)。我试图使用带有随机值的 cupy 和基准测试。到目前为止,我有以下代码:

import time
import contextlib
import cupy as cp
import numpy as np

squared_diff = cp.ElementwiseKernel(
    'float64 x, float64 y',
    'float64 z',
    'z = (x - y) * (x - y)',
    'squared_diff')

 x, y = np.random.randn(1000), np.random.randn(1000)
 x_gpu, y_gpu = cp.random.randn(1000), cp.random.randn(1000)

 c = np.zeros((len(x), len(y)))
 c_gpu = cp.zeros((len(x), len(y)))


 @contextlib.contextmanager
 def timer(message):
     cp.cuda.Stream.null.synchronize()
     start = time.time()
     yield
     cp.cuda.Stream.null.synchronize()
     end = time.time()
     print('%s:  %f sec' % (message, end - start))


with timer(' CPU '):
     for i in range(len(x)):
        for j in range(len(y)):
            c[i, j] = (x[i] - y[i]) ** 2

with timer(' GPU '):
     for i in range(len(x)):
         for j in range(len(y)):
            c_gpu[i, j] = squared_diff(x_gpu[i], y_gpu[j])

但是,与 CPU 相比,GPU 时间似乎要长得多。

CPU :  0.486763 sec
GPU :  26.627597 sec

在考虑使用 CUDA 提高计算速度背后的理论时,我是否遗漏了任何重要的提示或问题?

【问题讨论】:

如果我正确阅读了该代码(在 60 秒前我用谷歌搜索它之前我什至不知道 Cupy 是什么),你不是用单个元素有效地调用了该元素内核 1000000 次在每次通话中?如果是这样,那绝对不是使用 GPU 的明智之举 @talonmies:感谢您的回复。我正在寻找解决方案,我想我可以同意你的看法。似乎这是主要的开销。您有什么建议可以在这种情况下提高性能吗?看起来这个操作应该是并行的,因为所有的“单元”都是相互独立的。 我也刚刚注意到你的 GPU 和 CPU 版本也不做同样的操作 @talonmies:你能详细说明一下吗?操作看起来和我很相似。 相当相似不一样。仔细看主机代码 【参考方案1】:

您需要广播输入数组以进行元素计算。

def bcast(x, y, xp):
    return (xp.broadcast_to(x[:, None], (1000, 1000)),
            xp.broadcast_to(y, (1000, 1000)))

x, y = bcast(x, y, np)
with timer(' CPU '):
    c = (x - y) ** 2

x_gpu, y_gpu = bcast(x_gpu, y_gpu, cp)
with timer(' GPU '):
    c_gpu2 = squared_diff(x_gpu, y_gpu)

【讨论】:

以上是关于用cupy增加内环距离函数的主要内容,如果未能解决你的问题,请参考以下文章

Python 模块 Cupy 函数在使用 cupy.einsum() 时出错

我可以从c ++调用用cupy代码编写的cuda代码吗?

Cupy.unique() 函数中是不是有 CuPy 版本支持(轴)选项?任何解决方法?

为啥我系统上的所有 CuPy 函数都比它们的 NumPy 对应函数慢?

使用 cupy 从 GPU 上的另一个矩阵创建距离矩阵

Python GPU 加速数据科学 | 计算距离矩阵在用 cuPy 时快了约 100 倍