首页 > 解决方案 > 如何将 python 函数“any()”转换为 CUDA python 兼容代码(在 GPU 上运行)?

问题描述

我想知道如何any()在 GPU 上实现 numpy 函数(使用 Numba python)。any()函数接受一个数组,如果输入的True至少一个元素的计算结果为 ,则返回True

就像是:

@vectorize(["boolean(boolean)"], target='cuda')
def AnyFunction(a):
    return any(a)

或者

@vectorize(["boolean(boolean)"], target='cuda')
def AnyFunction(a):
    for i in range(len(a)):
        if a[i]==True:
            return True
    return False

标签: pythonnumpycudanumba

解决方案


函数操作的更困难的方面(也许)any是归约方面。对每个项目的真/假测试是一个可以很容易地用 eg 完成的操作vectorize,但是将许多结果组合成一个值(减少方面)不能(容易地);事实上vectorize,它并不是为了解决这类问题而设计的,至少不是直接的。

但是 numba cuda为简单的约简问题(例如这个)提供了一些帮助,而不会强迫您编写自定义的 numba cuda 内核。

这是一种可能的方法:

$ cat t20.py
import numpy
from numba import cuda

@cuda.reduce
def or_reduce(a, b):
    return a or b

A = numpy.ones(1000, dtype=numpy.int32)
B = numpy.zeros(1000, dtype=numpy.int32)
expect = A.any()      # numpy reduction
got = or_reduce(A)   # cuda reduction
print expect
print got
expect = B.any()      # numpy reduction
got = or_reduce(B)   # cuda reduction
print expect
print got
B[100] = 1
expect = B.any()      # numpy reduction
got = or_reduce(B)   # cuda reduction
print expect
print got

$ python t20.py
True
1
False
0
True
1
$

关于性能的一些评论:

  1. 这可能不是执行此操作的最快方法。但是我从您的问题中得到的印象是您正在寻找接近普通python的东西。
  2. 在 numba中编写自定义 CUDA 内核可能会更快地完成这项工作。
  3. 如果您对性能很认真,那么建议您尝试将此操作与其他要在 GPU 上完成的工作结合起来。在这种情况下,为了获得最大的灵活性,自定义内核将赋予您以最高性能完成任务的更多能力。

推荐阅读