我有一个来自Numpy repeat for 2d array的代码
下面的代码可以与numpy数组一起工作,但是会抛出
ValueError:具有多个元素的数组的真值不明确。与Cupy数组一起使用时,请使用a.any()或a.all()。
对于ret_val[mask] = cp.repeat(arr.ravel(), rep.ravel()
我试图使用Cupy中已经存在的逻辑运算,但是它们仍然会引发错误。
def repeat2dvect(arr, rep):
lens = cp.array(rep.sum(axis=-1))
maxlen = lens.max()
ret_val = cp.zeros((arr.shape[0], int(maxlen)))
mask = (lens[:,None]>cp.arange(maxlen))
ret_val[mask] = cp.repeat(arr.ravel(), rep.ravel())
return ret_val
答案 0 :(得分:1)
祝贺您对StackOverflow的首次贡献:)
我用以下代码复制了错误:
import cupy as cp
arr = cp.array([5, 1, 4], 'float32')
rep = cp.array([3, 2], 'int32')
result = cp.repeat(arr, rep)
ValueError: The truth value of an array with more than one element is ambiguous. Use a.any() or a.all()
此错误消息有点令人误解:该代码不起作用的原因有些不同。
简而言之,您不能将cp.ndarray
作为cp.repeat()
的第二个参数。
为什么?这是因为result
的形状是根据该参数的值确定的。
如果它是ndarray
,则在CuPy(而不是NumPy)中会出现问题,因为数组的值在GPU中。为了确定输出形状,CuPy必须等待GPU完成所有排队的计算,然后将值传输到CPU。那只会破坏异步计算的好处。 CuPy故意禁止此类操作。
在您的特定情况下,例如,您可以手动将rep
转换为np.ndarray
(通过ret.get()
),或者从一开始就将rep
计算为np.ndarray
。