numba
numba copied to clipboard
@guvectorize not accepting new size variable (i.e. () -> (n)) in output argument
MnWE:
from numba import guvectorize
@guvectorize("int64, int64[:]", "() -> (n)")
def result(x, res):
for i in range(3):
res[i] = x
if __name__ == "__main__":
print(result(3))
Yields the following error:
Traceback (most recent call last):
File "C:/Users/User/Documents/numba_playground/guvectorize_test.py", line 4, in <module>
@guvectorize("int64, int64[:]", "() -> (n)")
File "C:\Users\User\Anaconda3\lib\site-packages\numba\npyufunc\decorators.py", line 177, in wrap
guvec = GUVectorize(func, signature, **kws)
File "C:\Users\User\Anaconda3\lib\site-packages\numba\npyufunc\decorators.py", line 50, in __new__
targetoptions=kws)
File "C:\Users\User\Anaconda3\lib\site-packages\numba\npyufunc\ufuncbuilder.py", line 278, in __init__
self.sin, self.sout = parse_signature(signature)
File "C:\Users\User\Anaconda3\lib\site-packages\numba\npyufunc\sigparse.py", line 63, in parse_signature
raise NameError('undefined output symbols: %s' % ','.join(sorted(diff)))
NameError: undefined output symbols: n
Related to this discussion from 2016: https://groups.google.com/a/continuum.io/forum/#!topic/numba-users/tjkxRHj4x4k
Workaround there is to pass a dummy output array, like so:
@guvectorize("int64, int64[:], int64[:]", "(), (n) -> (n)")
def result2(x, dum, res):
for i in range(dum.shape[0]):
res[i] = x
Do mind the argument type for dum here, you'll likely have to explicitly declare it with dtype int64.
I just hit this issue. I would like to write a guvectorize'd function that returns an output of different size from the input. Is this possible?
The dummy output array approach really helps, thanks! But if I don't know the length of the output array originally, how can I solve this?
I also have this problem. Has anyone looked at a fix?
I also have this problem. Has anyone looked at a fix?
I would imagine not - any further updates would be likely to have been posted to this issue.
Joining the club, just hit this issue - (still) present in all pipelines, i.e. targets cpu
, parallel
, cuda
.
Does NumPy allow new size variables in output arguments for Generalized UFuncs?
Does NumPy allow new size variables in output arguments for Generalized UFuncs?
I think so?
Typically, the size of all core dimensions in an output will be determined by the size of a core dimension with the same label in an input array. This is not a requirement, and it is possible to define a signature where a label comes up for the first time in an output, although some precautions must be taken when calling such a function. An example would be the function euclidean_pdist(a), with signature (n,d)->(p), that given an array of n d-dimensional vectors, computes all unique pairwise Euclidean distances among them. The output dimension p must therefore be equal to n * (n - 1) / 2, but it is the caller’s responsibility to pass in an output array of the right size. If the size of a core dimension of an output cannot be determined from a passed in input or output array, an error will be raised.
https://numpy.org/doc/stable/reference/c-api/generalized-ufuncs.html