2017-08-23 26 views
0

示例代碼與NumPy的ufunc:numba.vectorize ufunc不支持timedelta64

import numpy as np 

nums = np.array([1, 2, 3]) 
times = nums.astype('timedelta64[ns]') 

np.less(nums, 2) 
np.less(nums, np.timedelta64(2)) 

這兩項均得到相同的結果:

array([ True, False, False], dtype=bool) 

現在我想要做同樣的事情與Numba:

import numba 

@numba.vectorize(nopython=True) 
def myless(a, b): 
    return a < b 

myless(nums, 2) 
myless(times, np.timedelta64(2)) # fails 

首先給出正確的結果,但第二次失敗:

TypeError: ufunc 'myless' not supported for the input types, and the inputs could not be safely coerced to any supported types according to the casting rule ''safe''

怎麼了?我該如何解決它?

回答

0

我發現在Numba 0.17發行說明的提示(它現在是一個很老的版本):

Issue #917: Allow vectorizing with datetime64 and timedelta64 in the signature (only with unit-less values, though, because of a Numpy limitation).

導致此comment

it seems numpy won't less us call ufuncs with non-unitless datetimes and timedeltas, so we're cooked [...]

因此很明顯,你永遠不能除非timedelta64沒有指定單位(在我的例子中,數組類型有[ns]納秒,甚至將單位添加到標量也沒有幫助),否則在nopython模式下使用帶有NumPy timedelta64的Numba矢量化ufunc。

0

這只是一種變通方法,但你總是可以零拷貝查看timedeltas爲整數(反之亦然)

In [80]: i8 = np.dtype('int64') 

In [81]: myless(times.view(i8), np.timedelta64(2).view(i8)) 
Out[81]: array([ True, False, False], dtype=bool) 
+1

是啊,雖然這使得很難在調用點。不好,因爲ufuncs的包裝會帶走所有的ufunc魔法。據我所知,你無法在任何地方隱藏黑客。另外,如果單位不同(如比較秒和納秒),您仍然需要一個副本。 –