9

C拡張機能でNumpy配列を操作したいと思います。この場合の多くの例では、PyArrayObjectの構造を使用しています。

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

データに到達するためのポインタ、より馴染みのある(またはよりきちんとした)方法で配列に到達したい場合は、次のようなインデックスを使用します

array[i][j]

どのように進めればよいですか?array-> dataを型キャスト(bool *)して、作成したC配列で作業する必要がありますか?(私の要素はboolsです)

今のところ私の関数宣言は(もちろん、まだ終わっていません)

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();
}

ありがとう!

4

4 に答える 4

2

これがあなたの質問に答えるかどうかはわかりませんが、CでNumPyデータに到達するために、Cで配列をループするイテレーターを作成することができます。それはあなたが求めているインデックスを提供しません([i] [j])ただし、アレイ全体をカバーします

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(...);
}
于 2013-09-13T16:38:59.980 に答える
1

これはあなたを助けるはずです。

http://mail.scipy.org/pipermail/numpy-discussion/2003-November/014837.html

于 2011-10-12T20:39:16.470 に答える
1

私はあなたがこれを見たいと思うでしょう:http://docs.scipy.org/doc/numpy/reference/c-api.array.html

特に、

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

と友達。これらは、APIが提供しなかった場合にDavidHeffernanが驚くであろう関数です。

于 2013-09-14T02:16:21.560 に答える
1

これはここでのすべての答えの中で最も汚いものだと思いますが、2年前、私はこの関数を次のように実装することになりました。

文書化するためにここに追加するだけです。あなたがこれを読んでいるなら、あなたはより良い他の解決策をチェックするべきです。

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

于 2013-09-20T20:33:26.117 に答える