2011-10-11 36 views
8

Tôi đang cố gắng hiểu cách Python C-Api hoạt động, và tôi muốn trao đổi các mảng numpy giữa Python và C Extension.Ví dụ về Numpy C-Api đưa ra một SegFault

Vì vậy, tôi bắt đầu hướng dẫn này: http://dsnra.jpl.nasa.gov/software/Python/numpydoc/numpy-13.html

Cố gắng để làm ví dụ đầu tiên ở đó, một mô-đun C cho phép tính dấu vết của một mảng NumPy 2d, rất gọn gàng cho tôi, vì tôi muốn làm các hoạt động tiểu học trong mảng 2d cũng có.

#include <Python.h> 
#include "Numeric/arrayobject.h" 
#include<stdio.h> 

int main(){ 
Py_Initialize(); 
import_array(); 
} 

static char doc[] = 
"This is the C extension for xor_masking routine"; 

    static PyObject * 
    trace(PyObject *self, PyObject *args) 
    { 
    PyObject *input; 
    PyArrayObject *array; 
    double sum; 
    int i, n; 

    if (!PyArg_ParseTuple(args, "O", &input)) 
    return NULL; 
    array = (PyArrayObject *) 
    PyArray_ContiguousFromObject(input, PyArray_DOUBLE, 2, 2); 
    if (array == NULL) 
    return NULL; 

    n = array->dimensions[0]; 
    if (n > array->dimensions[1]) 
    n = array->dimensions[1]; 
    sum = 0.; 
    for (i = 0; i < n; i++) 
    sum += *(double *)(array->data + i*array->strides[0] + i*array->strides[1]); 
    Py_DECREF(array); 
    return PyFloat_FromDouble(sum); 
    } 

static PyMethodDef TraceMethods[] = { 
    {"trace", trace, METH_VARARGS, doc}, 
    {NULL, NULL, 0, NULL} 
}; 

PyMODINIT_FUNC 
inittrace(void) 
{ 
    (void) Py_InitModule("trace", TraceMethods); 
} 


} 

tên của Module này là dấu vết, và nó được biên dịch với các tập tin setup.py:

from distutils.core import setup, Extension 

module = Extension('trace', sources = ['xor_masking.cpp']) 
setup(name = 'Trace Test', version = '1.0', ext_modules = [module]) 

Các tập tin được biên dịch, trace.so được nhập khẩu trong IPython, nhưng khi tôi cố gắng sử dụng phương thức trace(), tôi nhận được một lỗi Segmentation, tôi không biết tại sao.

tôi chạy này với Fedora 15, Python 2.7.1, gcc 4.3.0, 1.5.1 NumPy

+0

Lưu ý rằng hướng dẫn bạn đang theo dõi là dành cho * Numeric *, thư viện cũ được thay thế bởi Numpy hiện tại. Numpy là * chủ yếu là * tương thích ngược với nó, nhưng không hoàn toàn. (Có, cũng * Numeric * được gọi là "Numpy" không chính thức, dẫn đến nhầm lẫn ...) –

+0

Sau đó, tôi có nên nhập '#include" Numpy/arrayobject.h' thay thế? –

Trả lời

15

hàm init của bạn cho các mô-đun cần gọi

import_array(); 

sau

(void) Py_InitModule("trace", TraceMethods); 

Nó đề cập đến điều này trong hướng dẫn gần đầu, nhưng nó rất dễ bỏ sót. Nếu không có điều này, nó sẽ phân tách trên PyArray_ContiguousFromObject.

+0

Cảm ơn rất nhiều! Nó hoạt động giống như một sự quyến rũ –

+0

Wow, tôi đã phá vỡ đầu của tôi về điều này! –