我是一名生物物理学研究生,正在尝试使用 PyCUDA 和 Scipy 编写蛋白质聚合模型ODEInt
。在过去的两周内,我已经让代码运行起来了,但是速度很慢。让我看看我是否可以解释我的代码的作用。
我有np
一系列N
浓度,每个元素都是i+1
长度聚合物的浓度。我有一个函数可以计算聚合物浓度的变化率,CUDA
其中每个内核计算一种特定长度聚合物的变化率。在此计算过程中,(N-i-1)
线程需要对长度数组求和,从而大大降低了我的代码速度。
做一些阅读和谷歌搜索,我遇到了并行减少作为一种调用并行性的方式,以使像数组总和这样的串行计算变得更快。当然,我指的是 Mark Harris 的 powerpoint 幻灯片。这是一本很好的读物,这看起来是一种大幅加快我的代码速度的潜在方法,但我有几个问题:
如果聚合物种类的数量 N 需要为 ~ 8700-9000,是否可以使用 CUDA 同时减少这 N 个阵列?进行快速计算(再次感谢 SO 对如何计算最大并发线程数的出色解释),我得到了我的 GTX Titan 可以同时运行 15 * 64 * 32 = 30720 个线程。如果我一次在 ~8960 个内核上调用我的内核,我应该只剩下 21760 个线程可以使用,对吗?由于您似乎至少需要(数组的长度/ 2)线程才能正确减少它,所以我注定要失败。
我在想,也许我可以通过将剩余的线程分开并一次减少几个大数组来使用剩余的线程。
我不知道……我只是一名物理研究生。在我踏上错误方向的漫长旅程之前,我想我会问专业人士。是否可以轻松有效地告诉内核减少某些东西?
谢谢你,卡斯滕
这是我正在尝试做的事情的代表。
fluxes and concs are np.arrays
dcdt(concs, t)
Call CUDA to calculate fluxes
Thread
0 fluxes[i] = stuff + sum(concs[n] for n from 1 to 9000)
1 fluxes[i] = stuff + sum(concs[n] for n from 2 to 9000)
2 fluxes[i] = stuff + sum(concs[n] for n from 3 to 9000)
...
N fluxes[i] = stuff
您会注意到,我们一直在讨论的数组的总和基本上是每个线程的同一数组的较小版本。这让我想知道这是否是我应该在主机上做的事情。