Typecasting PyArrayObject data into C array

I want to work with my Numpy arrays in extension C. Many examples in this case use the PyArrayObject structure,

array->data , array->strides[0] , array->strides[1] , ...

to reach the data if I wanted to reach my array in a more familiar (or tidier) way with indices like

array[i][j]

how should i act like that? Should I output (bool *) an array-> data and work with the C array that I created? (my elements are bools)

Declaring my function yet (of course, not finished)

 static PyObject * xor_masking(PyObject *self, PyObject *args) { PyObject *input; PyObject *mask; PyObject *adjacency; PyObject *state; PyArrayObject *arr_mask; PyArrayObject *arr_adjacency; PyArrayObject *arr_state; PyArrayObject *arr_next_state; double sum; int counter_node, n_nodes; /* PyArg_ParseTuple * checks if from args, the pointers of type "O" can be extracted, and extracts them */ if (!PyArg_ParseTuple(args, "OOO:xor_masking_C", &mask, &adjacency, &state)) return NULL; /* * The pointer returned by PyArray_ContiguousFromObject is typecasted to * a PyArrayObject Pointer and array is pointed to the same address. */ arr_mask = (PyArrayObject *) PyArray_ContiguousFromObject(mask, PyArray_BOOL, 2, 2); arr_adjacency = (PyArrayObject *) PyArray_ContiguousFromObject(adjacency, PyArray_BOOL, 2, 2); arr_state = (PyArrayObject *) PyArray_ContiguousFromObject(state, PyArray_BOOL, 2, 2); if (array == NULL) return NULL; int n_mask_0 = mask->dimensions[0]; int n_mask_1 = mask->dimensions[1]; int n_adjacency_0 = adjacency->dimensions[0]; int n_adjacency_1 = adjacency->dimensions[1]; int n_state_0 = state->dimensions[0]; int n_nodes = n_state_0; /* * if the dimensions don't match, return NULL */ bool c_mask[n_nodes][n_nodes]; if (n_mask_0 != n_mask_1 || n_adjacency_0 != n_adjacency_1 || n_adjacency_0 != n_mask_0 || n_adjacency_0 != n_adjacency_1) { return NULL; } /* * The 2D arrays are introduced as follows * array[i][j] = (array->data + i*array->strides[0] + j*array->strides[1]) */ for (counter_node = 0; i < n_mask; i++){ *row_start = (array->data + i*array->strides[0]); } //Py_DECREF(); //return PyFloat_FromDouble(); } 

Thanks!

+6
source share
4 answers

I think you might want to look at this: http://docs.scipy.org/doc/numpy/reference/c-api.array.html

In particular,

 void* PyArray_GETPTR3(PyObject* obj, <npy_intp> i, <npy_intp> j, <npy_intp> k) 

and friends. These are the features that David Heffernan would have been surprised if the API did not provide.

+1
source

I'm not sure if this question answers your question, but in order to reach your NumPy data in C, you can try to create an iterator to iterate over your array in C. It does not give you indexing after ([i] [j]), but it spans the entire array

 static PyObject *func1(PyObject *self, PyObject *args) { PyArrayObject *X; int ndX; npy_intp *shapeX; NpyIter *iter; NpyIter_IterNextFunc *iternext; PyArray_Descr *dtype; double **dataptr; PyArg_ParseTuple(args, "O!", &PyArray_Type, &X); ndX = PyArray_NDIM(X); shapeX = PyArray_SHAPE(X); dtype = PyArray_DescrFromType(NPY_DOUBLE); iter = NpyIter_New(X, NPY_ITER_READONLY, NPY_KEEPORDER, NPY_NO_CASTING, dtype); iternext = NpyIter_GetIterNext(iter, NULL); dataptr = (double **) NpyIter_GetDataPtrArray(iter); do { cout << **dataptr << endl; //Do something with the data in your array } while (iternext(iter)); NpyIter_Deallocate(iter); return Py_BuildValue(...); } 
+1
source

This is the dirtiest of all the answers here, I think, but 2 years ago I ended up implementing this function as follows:

Just add it for documentation. If you are reading this, you should check out other solutions that are better.

https://gist.github.com/mehmetalianil/6643299

+1
source

Source: https://habr.com/ru/post/899157/


All Articles