MCPcopy Create free account
hub / github.com/numpy/numpy / PyUFunc_AddWrappingLoop

Function PyUFunc_AddWrappingLoop

numpy/core/src/umath/wrapping_array_method.c:225–337  ·  view source on GitHub ↗

* Allows creating of a fairly lightweight wrapper around an existing ufunc * loop. The idea is mainly for units, as this is currently slightly limited * in that it enforces that you cannot use a loop from another ufunc. * * @param ufunc_obj * @param new_dtypes * @param wrapped_dtypes * @param translate_given_descrs See typedef comment * @param translate_loop_descrs See typedef comment *

Source from the content-addressed store, hash-verified

223 * @return 0 on success -1 on failure
224 */
225NPY_NO_EXPORT int
226PyUFunc_AddWrappingLoop(PyObject *ufunc_obj,
227 PyArray_DTypeMeta *new_dtypes[], PyArray_DTypeMeta *wrapped_dtypes[],
228 translate_given_descrs_func *translate_given_descrs,
229 translate_loop_descrs_func *translate_loop_descrs)
230{
231 int res = -1;
232 PyUFuncObject *ufunc = (PyUFuncObject *)ufunc_obj;
233 PyObject *wrapped_dt_tuple = NULL;
234 PyObject *new_dt_tuple = NULL;
235 PyArrayMethodObject *meth = NULL;
236
237 if (!PyObject_TypeCheck(ufunc_obj, &PyUFunc_Type)) {
238 PyErr_SetString(PyExc_TypeError,
239 "ufunc object passed is not a ufunc!");
240 return -1;
241 }
242
243 wrapped_dt_tuple = PyArray_TupleFromItems(
244 ufunc->nargs, (PyObject **)wrapped_dtypes, 1);
245 if (wrapped_dt_tuple == NULL) {
246 goto finish;
247 }
248
249 PyArrayMethodObject *wrapped_meth = NULL;
250 PyObject *loops = ufunc->_loops;
251 Py_ssize_t length = PyList_Size(loops);
252 for (Py_ssize_t i = 0; i < length; i++) {
253 PyObject *item = PyList_GetItem(loops, i);
254 PyObject *cur_DType_tuple = PyTuple_GetItem(item, 0);
255 int cmp = PyObject_RichCompareBool(cur_DType_tuple, wrapped_dt_tuple, Py_EQ);
256 if (cmp < 0) {
257 goto finish;
258 }
259 if (cmp == 0) {
260 continue;
261 }
262 wrapped_meth = (PyArrayMethodObject *)PyTuple_GET_ITEM(item, 1);
263 if (!PyObject_TypeCheck(wrapped_meth, &PyArrayMethod_Type)) {
264 PyErr_SetString(PyExc_TypeError,
265 "Matching loop was not an ArrayMethod.");
266 goto finish;
267 }
268 break;
269 }
270 if (wrapped_meth == NULL) {
271 PyErr_Format(PyExc_TypeError,
272 "Did not find the to-be-wrapped loop in the ufunc with given "
273 "DTypes. Received wrapping types: %S", wrapped_dt_tuple);
274 goto finish;
275 }
276
277 PyType_Slot slots[] = {
278 {NPY_METH_resolve_descriptors, &wrapping_method_resolve_descriptors},
279 {_NPY_METH_get_loop, &wrapping_method_get_loop},
280 {NPY_METH_get_reduction_initial,
281 &wrapping_method_get_identity_function},
282 {0, NULL}

Callers 1

sfloat_add_wrapping_loopFunction · 0.85

Calls 3

PyArray_TupleFromItemsFunction · 0.85
PyUFunc_AddLoopFunction · 0.85

Tested by

no test coverage detected