Python и динамически расширяемые классы C++

Поэтому я столкнулся с проблемой с моими пользовательскими типами, функциями и атрибутами в Python.

Когда я нахожусь в Python, и я хочу установить атрибут для одного из моих пользовательских типов (например, Vector4), мой код получает NULL для const char* attribute_name аргумент (и да, я импортирую свой модуль).

Как ни странно, когда я жестко кодирую имя атрибута в своей функции установки, я получаю ошибку:

SystemError: error return without exception set

Я вижу, как объект создается в Python (и снова в C++), поэтому я не думаю, что это проблема. Я возвращаю 1, если ловушка setattro успешно установила атрибут в C++, и я вижу, как вызывается код и задает атрибут на стороне C++. Нет ошибок / исключений, которые возникают при установке атрибута.

Кроме того, когда я вызываю функцию в экземпляре моего класса в Python, она вызывает функцию, установленную в tp_getattro вместо проверки словаря.

Я не совсем уверен, почему, может быть, это потому, что я устанавливаю словарь и помещаю туда свои функции вместо того, чтобы делать это через PyModuleDef массив, таким образом, функции не видны, когда PyType_Ready называется.

У кого-нибудь есть идеи, почему это может происходить? Мы используем Python 3.2.


Соответствующий:

У меня базовый тип (tp_new а также tp_dealloc), а затем я создаю производные типы во время выполнения. Производные типы имеют словарь, tp_base, tp_getattro и tp_setattro,

Вот как функции связаны с классом / типами Python:

PyMethodDef newMethod;
newMethod.ml_doc = newMethod.ml_name = funcName;
newMethod.ml_flags = METH_VARARGS;
newMethod.ml_meth = pythonFunc;

PyGeneralObj* selfFake = PyObject_New(PyGeneralObj, &MetaEngineType);
selfFake->className = className;
selfFake->funcName = funcName;
Py_INCREF((PyObject*)selfFake);

PyObject *func = PyCFunction_New(&newMethod, (PyObject*)selfFake);
PyObject *method = PyInstanceMethod_New(func);

ErrorIf((method == NULL), "Python: Cannot create instance function. %s", 
funcName);

ErrorIf((PyDict_SetItem(classObj->m_pyClassType->tp_dict,            
PyReturnStr(newMethod.ml_name), method) == -1), 
"Python: Cannot create function in dictionary.");

Py_DECREF(func);
Py_DECREF(method);

Где funcName и className являются константными символами *. pythonFunc - это универсальная функция python, которая обрабатывает вызов всех наших функций, связанных с нашей мета-системой. classObj - указатель на PythonClass, который имеет член m_pyClassType (тип PyTypeObject).

PyGeneralObj новый объект имеет два const char * и void* (это объект в C++)

я делаю PyType_Ready и не получить ошибок, а затем увеличить мой тип. Затем я добавляю объект в модуль PyObject, который мне дан PyImport_ImportModule, Я добавляю свой основной модуль во время выполнения, инициализирую python и импортирую мой модуль.


Если нужно больше информации / кода, я могу опубликовать еще немного. Надеюсь, это имеет смысл, это мой первый пост на stackru.

Для пояснения мы хотим иметь динамические атрибуты, которые полностью разрешаются на стороне C++. И для функций, я хочу иметь возможность переопределить PyObject* self аргумент, чтобы я мог получить строковое имя функции, которая должна быть вызвана.

Мы не хотим использовать сторонние библиотеки / интерфейсы, такие как Boost, Cython и другие.

1 ответ

Решение

Проблема была в моей реализации getattro.

Другие вопросы по тегам