diff options
author | mattip <matti.picus@gmail.com> | 2018-04-30 11:37:31 +0300 |
---|---|---|
committer | Marten van Kerkwijk <mhvk@astro.utoronto.ca> | 2018-05-28 13:41:21 -0400 |
commit | d0e5e394d9174d3d5651aacc98b1cb6fcdcc75b2 (patch) | |
tree | b3c465d305dc84561592559b5a09864bf2482a3c /numpy | |
parent | 69458b02956d39082014573eb0350ae3eb3436ee (diff) | |
download | numpy-d0e5e394d9174d3d5651aacc98b1cb6fcdcc75b2.tar.gz |
TST: Test dimensions/indices found from parsed gufunc signatures.
Diffstat (limited to 'numpy')
-rw-r--r-- | numpy/core/src/umath/_umath_tests.c.src | 62 | ||||
-rw-r--r-- | numpy/core/tests/test_ufunc.py | 17 |
2 files changed, 67 insertions, 12 deletions
diff --git a/numpy/core/src/umath/_umath_tests.c.src b/numpy/core/src/umath/_umath_tests.c.src index 120ce0332..76af40439 100644 --- a/numpy/core/src/umath/_umath_tests.c.src +++ b/numpy/core/src/umath/_umath_tests.c.src @@ -317,13 +317,16 @@ addUfuncs(PyObject *dictionary) { static PyObject * UMath_Tests_test_signature(PyObject *NPY_UNUSED(dummy), PyObject *args) { - int nin, nout; + int nin, nout, i; PyObject *signature, *sig_str; - PyObject *f; + PyUFuncObject *f = NULL; + PyObject *core_num_dims = NULL, *core_dim_ixs = NULL; int core_enabled; + int core_num_ixs = 0; - if (!PyArg_ParseTuple(args, "iiO", &nin, &nout, &signature)) return NULL; - + if (!PyArg_ParseTuple(args, "iiO", &nin, &nout, &signature)) { + return NULL; + } if (PyString_Check(signature)) { sig_str = signature; @@ -334,17 +337,60 @@ UMath_Tests_test_signature(PyObject *NPY_UNUSED(dummy), PyObject *args) return NULL; } - f = PyUFunc_FromFuncAndDataAndSignature(NULL, NULL, NULL, + f = (PyUFuncObject*)PyUFunc_FromFuncAndDataAndSignature( + NULL, NULL, NULL, 0, nin, nout, PyUFunc_None, "no name", "doc:none", 1, PyString_AS_STRING(sig_str)); if (sig_str != signature) { Py_DECREF(sig_str); } - if (f == NULL) return NULL; - core_enabled = ((PyUFuncObject*)f)->core_enabled; + if (f == NULL) { + return NULL; + } + core_enabled = f->core_enabled; + /* + * Don't presume core_num_dims and core_dim_ixs are defined; + * they currently are even if core_enabled=0, but there's no real + * reason they should be. So avoid segfaults if we change our mind. + */ + if (f->core_num_dims != NULL) { + core_num_dims = PyTuple_New(f->nargs); + if (core_num_dims == NULL) { + goto fail; + } + for (i = 0; i < f->nargs; i++) { + PyObject *val = PyLong_FromLong(f->core_num_dims[i]); + PyTuple_SET_ITEM(core_num_dims, i, val); + core_num_ixs += f->core_num_dims[i]; + } + } + else { + Py_INCREF(Py_None); + core_num_dims = Py_None; + } + if (f->core_dim_ixs != NULL) { + core_dim_ixs = PyTuple_New(core_num_ixs); + if (core_num_dims == NULL) { + goto fail; + } + for (i = 0; i < core_num_ixs; i++) { + PyObject * val = PyLong_FromLong(f->core_dim_ixs[i]); + PyTuple_SET_ITEM(core_dim_ixs, i, val); + } + } + else { + Py_INCREF(Py_None); + core_dim_ixs = Py_None; + } Py_DECREF(f); - return Py_BuildValue("i", core_enabled); + return Py_BuildValue("iOO", core_enabled, core_num_dims, core_dim_ixs); + +fail: + Py_XDECREF(f); + Py_XDECREF(core_num_dims); + Py_XDECREF(core_dim_ixs); + return NULL; } static PyMethodDef UMath_TestsMethods[] = { diff --git a/numpy/core/tests/test_ufunc.py b/numpy/core/tests/test_ufunc.py index a5b9ce76f..b7fda3f2e 100644 --- a/numpy/core/tests/test_ufunc.py +++ b/numpy/core/tests/test_ufunc.py @@ -285,10 +285,16 @@ class TestUfunc(object): def test_signature(self): # the arguments to test_signature are: nin, nout, core_signature # pass - assert_equal(umt.test_signature(2, 1, "(i),(i)->()"), 1) + enabled, num_dims, ixs = umt.test_signature(2, 1, "(i),(i)->()") + assert_equal(enabled, 1) + assert_equal(num_dims, (1, 1, 0)) + assert_equal(ixs, (0, 0)) - # pass. empty core signature; treat as plain ufunc (with trivial core) - assert_equal(umt.test_signature(2, 1, "(),()->()"), 0) + # empty core signature; treat as plain ufunc (with trivial core) + enabled, num_dims, ixs = umt.test_signature(2, 1, "(),()->()") + assert_equal(enabled, 0) + assert_equal(num_dims, (0, 0, 0)) + assert_equal(ixs, ()) # in the following calls, a ValueError should be raised because # of error in core signature @@ -327,7 +333,10 @@ class TestUfunc(object): pass # more complicated names for variables - assert_equal(umt.test_signature(2, 1, "(i1,i2),(J_1)->(_kAB)"), 1) + enabled, num_dims, ixs = umt.test_signature(2, 1, "(i1,i2),(J_1)->(_kAB)") + assert_equal(enabled, 1) + assert_equal(num_dims, (2, 1, 1)) + assert_equal(ixs, (0, 1, 2, 3)) def test_get_signature(self): assert_equal(umt.inner1d.signature, "(i),(i)->()") |