Я немного борюсь с API Python C. Я вызываю метод python для выполнения AI игры около 60 Гц. Он работает больше всего времени, но каждый второй или около того вызов PyEval_CallObject приводит к возвращаемому значению NULL. Если я правильно обнаружу ошибку и продолжу цикл, все будет хорошо в течение следующей секунды или около того, после чего ошибка снова возникнет.PyEval_CallObject сбой в цикле иногда
Я подозреваю, что я делаю что-то неправильно с подсчетом реф, но я не могу понять, что это такое:
int script_do_ai(struct game_data_t* gd)
{
PyObject *pAiModule, *pResult;
float result=0.0;
pResult = NULL;
pAiModule = PyImport_Import(PyString_FromString("ai_script"));
Да, я импортировать модуль каждой итерации. Это необходимо? Если я буду хранить pAiModule как глобальный, я получаю жесткий сбой примерно через секунду.
pResult = PyEval_CallObject(PyObject_GetAttrString(pAiModule, "do_ai"),
Py_BuildValue("f", gd->important_float))
if (pResult != NULL)
{
PyArg_Parse(pResult, "f", &result);
Py_DECREF(pResult);
ConquerEnemies(result); //you get the idea
}
else //this happens every 75 or so iterations thru the loop
{
if (PyErr_ExceptionMatches(PyExc_SomeException)) //? not sure what to do here
{
Я не был в состоянии выяснить, как извлечь исключение еще, либо ... без тестирования каждый исключение
}
}
Am Я даже близко к делать это правильно? Как я уже сказал, он работает в основном, но мне очень хотелось бы понять, почему я получаю сообщение об ошибке.
Заранее благодарю за любую помощь.
+1 спасибо ... Я подумал, что если бы я включил вызов Py_BuildValue, он позаботился бы о протекающей ссылке, но, возможно, нет. Я посмотрю, что PyErr_Fetch дает мне на pyErr_Occured –
Увы, C не сбор мусора :) PyErr_Print() довольно удобен для печати исключений, особенно при отладке подобных случаев. –
Да, слишком много времени в .NET-land для меня. Хорошо, странно. Я добавил «sys.stdout = open ('CONOUT $', 'wt')" в свой скрипт python (для вывода на консоль ... я нахожусь в Win32), и все началось магически. Bizarre. –