bearoplane
bearoplane

Reputation: 820

cdef extern custom types in Cython

I am using Cython to interface some C functionality with a Python application I am writing. I've practiced using Cython to call C code from Python before, with the code below demonstrating an example of what I normally do in .pyx files:

# wrapper.pyx

cdef extern from "customlib.h":
    int my_function(int value)

def call_c_code(value):
    output_value = engine(value)
    print(output_value)

...using my customlib.h file:

#ifndef CUSTOM_HEADER_H
#define CUSTOM_HEADER_H

/* function */
int my_function(int value);

#endif

...and then the corresponding Python implementation to call the function:

# caller.py

import wrapper

wrapper.call_c_code(5) # and then the result is printed... etc.

This works just fine. However, what if my_function is of a user-defined type, rather than int, double, etc.? The C code I am trying to interface with defines this struct

typedef struct 
{
    double *data;                 /* a 1D data array of type double */
    int nd;                       /* the number of dimensions */
    unsigned long *dimensions;    /* an array that contains the size of each dimension */
    unsigned long num_elem;       /* the number of elements in this array (cumprod(dimensions)) */
} dataArray_double;

and then defines functions with dataArray_double as both a return type and the types of some inputs.

What steps do I need to take to build my Cython interface code out to use functions with this custom type?

Upvotes: 2

Views: 2420

Answers (1)

Pierre de Buyl
Pierre de Buyl

Reputation: 7293

You must create a container class that holds the C variable. A C variable (apart from numbers and characters) cannot be passed "as is" at the Python level. Look also for PyCapsule if you want a standard solution here.

In short, add the struct in the cdef extern from "customlib.h": part of your code and it will be available at the Cython level.

Upvotes: 2

Related Questions