从Python到C和从C到Python的数据转换

0 投票
2 回答
541 浏览
提问于 2025-04-17 04:45

在Cython中,像整数(int)或字符(char)这样的类型转换是自动进行的,但如果我使用一个

       cdef struct MyClass_Tag:
            pass
      ctypedef MyClass_Tag* MyClass_ptr
      ....
      cdef class MyClass:
           cdef MyClass_ptr obj
           ....

现在为了包装任何函数,比如在C语言中有一个叫foo的函数,它接受

      foo(char* , MyClass_ptr self)
           #return stuff

要包装这个函数,我这样做:

       def py_foo(char* n, self):
            return foo(n,self.obj)

所以从Python到C语言:

       char is done automatically
       but self is of type MyClass so to call the foo i have to write self.obj , 
       so i pass the same obj

在这里就是从Python到C语言的转换发生的地方。

问题是我不明白从C语言到Python的转换在哪里发生,我是说具体在哪个点上发生的?

即使在这种情况下,或者如果你给我其他例子也可以。谢谢!

2 个回答

0

我不是很明白你的问题,不过你可以试试这个命令:

cython -a <yourfile.pyx>

然后,用你的网页浏览器打开生成的文件。你会看到Cython是如何把你的代码翻译成C语言的,这样你就能找到你的答案了 :)

0

根据参数名 self 的意思,C 语言中的 foo() 函数在 Python 中作为一个方法可能更合适:

cdef extern void c_foo "foo" (char* n, MyClass_ptr)

cdef class MyClass:
   cdef MyClass_ptr this

   def foo(self, unicode n not None):
       b = n.encode('ascii')
       cdef char* p = b
       c_foo(p, self.this)

另外可以参考 包装 C 库

Cython 会把你的代码转换成 C(或者 C++)。到这个时候,你可以忘记它的存在。生成的 C 代码就是一个普通的 Python 扩展。这段代码包含了一些普通的 Python C API 调用,比如 PyBytes_AsString()(把 Python 的 bytes 转换成 char*)或者 PyInt_FromLong()(把 C 的 int 转换成 Python 的整数)。

MyClass_ptr 就是直接使用:

struct __pyx_obj_3foo_MyClass {
  PyObject_HEAD
  MyClass_ptr this; /* <-- using MyClass_ptr as is */
};

也就是说,纯 Python 代码根本看不到它,所以没有从 Python 对象之间的转换。

撰写回答