summaryrefslogtreecommitdiff
path: root/numpy/core/numeric.py
diff options
context:
space:
mode:
authorSebastian Berg <sebastian@sipsolutions.net>2021-12-07 20:17:17 -0600
committerSebastian Berg <sebastianb@nvidia.com>2023-01-17 18:40:44 +0100
commit60a858a372b14b73547baacf4a472eccfade1073 (patch)
tree1061a985383ad6ab2a8dc56f144ec25cfbff071e /numpy/core/numeric.py
parent9b6a7b4f874f5502112f36d485b12d92889eb808 (diff)
downloadnumpy-60a858a372b14b73547baacf4a472eccfade1073.tar.gz
ENH: Improve array function overhead by using vectorcall
This moves dispatching for `__array_function__` into a C-wrapper. This helps speed for multiple reasons: * Avoids one additional dispatching function call to C * Avoids the use of `*args, **kwargs` which is slower. * For simple NumPy calls we can stay in the faster "vectorcall" world This speeds up things generally a little, but can speed things up a lot when keyword arguments are used on lightweight functions, for example:: np.can_cast(arr, dtype, casting="same_kind") is more than twice as fast with this. There is one alternative in principle to get best speed: We could inline the "relevant argument"/dispatcher extraction. That changes behavior in an acceptable but larger way (passes default arguments). Unless the C-entry point seems unwanted, this should be a decent step in the right direction even if we want to do that eventually, though. Closes gh-20790 Closes gh-18547 (although not quite sure why)
Diffstat (limited to 'numpy/core/numeric.py')
-rw-r--r--numpy/core/numeric.py37
1 files changed, 8 insertions, 29 deletions
diff --git a/numpy/core/numeric.py b/numpy/core/numeric.py
index 577f8e7cd..91e35c684 100644
--- a/numpy/core/numeric.py
+++ b/numpy/core/numeric.py
@@ -130,10 +130,6 @@ def zeros_like(a, dtype=None, order='K', subok=True, shape=None):
return res
-def _ones_dispatcher(shape, dtype=None, order=None, *, like=None):
- return(like,)
-
-
@set_array_function_like_doc
@set_module('numpy')
def ones(shape, dtype=None, order='C', *, like=None):
@@ -187,16 +183,13 @@ def ones(shape, dtype=None, order='C', *, like=None):
"""
if like is not None:
- return _ones_with_like(shape, dtype=dtype, order=order, like=like)
+ return _ones_with_like(like, shape, dtype=dtype, order=order)
a = empty(shape, dtype, order)
multiarray.copyto(a, 1, casting='unsafe')
return a
-
-_ones_with_like = array_function_dispatch(
- _ones_dispatcher
-)(ones)
+_ones_with_like = array_function_dispatch()(ones)
def _ones_like_dispatcher(a, dtype=None, order=None, subok=None, shape=None):
@@ -323,7 +316,7 @@ def full(shape, fill_value, dtype=None, order='C', *, like=None):
"""
if like is not None:
- return _full_with_like(shape, fill_value, dtype=dtype, order=order, like=like)
+ return _full_with_like(like, shape, fill_value, dtype=dtype, order=order)
if dtype is None:
fill_value = asarray(fill_value)
@@ -333,9 +326,7 @@ def full(shape, fill_value, dtype=None, order='C', *, like=None):
return a
-_full_with_like = array_function_dispatch(
- _full_dispatcher
-)(full)
+_full_with_like = array_function_dispatch()(full)
def _full_like_dispatcher(a, fill_value, dtype=None, order=None, subok=None, shape=None):
@@ -1778,10 +1769,6 @@ def indices(dimensions, dtype=int, sparse=False):
return res
-def _fromfunction_dispatcher(function, shape, *, dtype=None, like=None, **kwargs):
- return (like,)
-
-
@set_array_function_like_doc
@set_module('numpy')
def fromfunction(function, shape, *, dtype=float, like=None, **kwargs):
@@ -1847,15 +1834,13 @@ def fromfunction(function, shape, *, dtype=float, like=None, **kwargs):
"""
if like is not None:
- return _fromfunction_with_like(function, shape, dtype=dtype, like=like, **kwargs)
+ return _fromfunction_with_like(like, function, shape, dtype=dtype, **kwargs)
args = indices(shape, dtype=dtype)
return function(*args, **kwargs)
-_fromfunction_with_like = array_function_dispatch(
- _fromfunction_dispatcher
-)(fromfunction)
+_fromfunction_with_like = array_function_dispatch()(fromfunction)
def _frombuffer(buf, dtype, shape, order):
@@ -2130,10 +2115,6 @@ def _maketup(descr, val):
return tuple(res)
-def _identity_dispatcher(n, dtype=None, *, like=None):
- return (like,)
-
-
@set_array_function_like_doc
@set_module('numpy')
def identity(n, dtype=None, *, like=None):
@@ -2168,15 +2149,13 @@ def identity(n, dtype=None, *, like=None):
"""
if like is not None:
- return _identity_with_like(n, dtype=dtype, like=like)
+ return _identity_with_like(like, n, dtype=dtype)
from numpy import eye
return eye(n, dtype=dtype, like=like)
-_identity_with_like = array_function_dispatch(
- _identity_dispatcher
-)(identity)
+_identity_with_like = array_function_dispatch()(identity)
def _allclose_dispatcher(a, b, rtol=None, atol=None, equal_nan=None):