Как можно определить значение #defined C для Python в модуле Cython?

Я хотел бы сделать целые константы (ACTIVE_TAG и т.д.), определенные здесь:

//island management, m_activationState1
#define ACTIVE_TAG 1
#define ISLAND_SLEEPING 2
#define WANTS_DEACTIVATION 3
#define DISABLE_DEACTIVATION 4
#define DISABLE_SIMULATION 5

доступен как обычные атрибуты модуля Cython, над которым я работаю, так что код приложения Python может получить к ним доступ (передать их в завернутые API, которые определены в терминах их).

Я рассмотрел их определение с помощью cdef как целых чисел или перечислений, но ни один из этих подходов фактически не привязывает значение к атрибуту в модуле Cython. Какие еще существуют варианты?

Ответы

Ответ 1

Здесь один из способов, который, хотя и кажущийся утомительным, может быть автоматизирован для любого заданного файла .h в качестве входного файла:

Шаг 1. Получите все константы, которые вы хотите в файл, скажем bulletdefs.h, у которого есть #defines, но с ведущими подчеркиваниями, например:

#define _ACTIVE_TAG 1
#define _ISLAND_SLEEPING 2
#define _WANTS_DEACTIVATION 3
#define _DISABLE_DEACTIVATION 4
#define _DISABLE_SIMULATION 5

Шаг 2. Вставьте раздел в файл pyx для вашего модуля, скажем bullet.pyx:

cdef extern from "bulletdefs.h":
    cdef int _ACTIVE_TAG
    cdef int _ISLAND_SLEEPING
    cdef int _WANTS_DEACTIVATION
    cdef int _DISABLE_DEACTIVATION
    cdef int _DISABLE_SIMULATION

ACTIVE_TAG = _ACTIVE_TAG
ISLAND_SLEEPING = _ISLAND_SLEEPING
WANTS_DEACTIVATION = _WANTS_DEACTIVATION
DISABLE_DEACTIVATION = _DISABLE_DEACTIVATION
DISABLE_SIMULATION = _DISABLE_SIMULATION

Затем, когда вы компилируете свой модуль, вы должны получить предполагаемый эффект:

Python 2.7.1+ (r271:86832, Apr 11 2011, 18:05:24) 
[GCC 4.5.2] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> import bullet
>>> bullet.ACTIVE_TAG
1
>>> bullet.DISABLE_SIMULATION
5
>>>