2016-02-24 4 views
0

У меня есть функция C, которая принимает указатель на struct, и я хочу использовать ее в python с помощью C-Extensions by Cython way, но когда я хочу передать указатель на struct из python, дайте me ошибка: «Невозможно преобразовать объект Python в« Foo * »» В приведенном ниже примере я делаю объект для вызова функции C, но то, что передается функции C, является указателем NULL.Cython - Укладку указателя на структуру от C до python

My Trial:

hello.h

#include <stdio.h> 

typedef struct 
{ 
    int x; 
} Foo; 

int hello(Foo* what); 

hello.c

#include "hello.h" 

int hello(Foo* what) 
{ 
    printf("Hello Wrapper\n"); 
    printf("what: %p\n", what); 
    what->x = 5; 
    return what->x; 
} 

phello.pxd

cdef extern from "hello.h": 
    ctypedef struct Foo: 
     int x 

    cdef int hello(Foo* what) 

phello.pyx

cimport phello 

cdef class Foo_c: 
    cdef phello.Foo* s 

    def hello_fn(self): 
     return phello.hello(self.s) 

setup.py

from distutils.core import setup, Extension 
from Cython.Distutils import build_ext 

setup(
cmdclass = {'build_ext': build_ext}, 
ext_modules=[ Extension("hellomodule", 
         sources=["phello.pyx", "hello.c"], 
         ) ] 

test.py

import hellomodule 

print "Hello test.py" 

tobject = hellomodule.Foo_c() 
print "Object:", tobject 

tobject.hello_fn() 

Так я хочу создать "Foo" структуры в "test.py" и передать его в "hello_fn) (" функция вызовите функцию «hello()» после передачи этой структуры, поэтому я могу читать или писать на этой структуре с обеих сторон. python & C.

Может ли кто-нибудь помочь мне в этом, пожалуйста?

+0

Я считаю, что вы только что получили ошибку с отступом, а 'hello_fn' не имеет отступов, поэтому он связан с классом' Foo_c'. С его отступом правильно он компилируется для меня. К сожалению, это невозможно сказать, потому что форматирование кода является беспорядком в вопросе. – DavidW

+0

@DavidW Извините за отступ промаха, да, он работает правильно, но мой вопрос заключался в том, как создать структуру типа «Foo» и заполнить ее в «test.py», а затем передать ее «int hello (Foo * what)» на функция python оболочки «hello_fn()». –

ответ

0

Ваш код не выделяет память для phello.Foo. Выделение может быть сделано в __cinit__ с calloc (или malloc) и освобождением в __dealloc__ с бесплатным.

cimport phello 
from libc.stdlib cimport calloc, free 

cdef class Foo_c: 
    cdef phello.Foo* s 

    def __cinit__(self, int n): 
     self.s = <phello.Foo *>calloc(1, sizeof(phello.Foo)) 

    def __dealloc__(self): 
     free(<void *>self.s) 

    def __init__(self, int n): 
     self.s.x = n 
Смежные вопросы