Conventions for memory management and destructors / free() with Python's CFFI?

天大地大妈咪最大 提交于 2020-01-03 16:53:37

问题


If I'm wrapping a C class:

from ._ffi import ffi, lib

class MyClass(object):
     def __init__(self):
         self._c_class = lib.MyClass_create()

What are best practices for making sure that lib.MyClass_destroy(…) is called?

Does cffi have some sort of wrapper around objects that will call a destructor when the Python object is GC'd, for example something like:

my_obj = managed(lib.MyClass_create(), destructor=lib.MyClass_destroy)

Or should that destructor logic be in the class's __del__? Something like:

class MyClass(object):
    def __del__(self):
        if self._c_class is not None:
            lib.MyClass_destroy(self._c_class)

What are the best practices here?


回答1:


It looks like ffi.gc() is the way to go. This is the small wrapper I've written which also does the post-malloc NULL check:

def managed(create, args, free):
    o = create(*args)
    if o == ffi.NULL:
        raise MemoryError("%s could not allocate memory" %(create.__name__, ))
    return ffi.gc(o, free)

For example:

c_class = managed(lib.MyClass_create, ("some_arg", 42),
                  lib.MyClass_destroy)


来源:https://stackoverflow.com/questions/30811104/conventions-for-memory-management-and-destructors-free-with-pythons-cffi

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!