无法从嵌入的Python返回长整型到C++
你好,我正在尝试从嵌入的Python代码返回一个值(119599936)到C++。
Py_Initialize();
PyObject* myModuleString = PyString_FromString((char*)"memory_leak_test");
PyObject* myModule = PyImport_Import(myModuleString);
PyObject* myFunction = PyObject_GetAttrString(myModule,(char*)"begin");
PyObject* args = PyTuple_Pack(1,PyString_FromString("CacheSetup"));
PyObject* myResult = PyObject_CallObject(myFunction, args);
double result = PyFloat_AsDouble(myResult);// <<<<<<<<< I guess thts where i'm goin wrong
std::cout << result << std::endl;
Py_Finalize();
我试过了。
unsigned long result = PyLong_AsUnsignedLong(myResult);
unsigned long long result = PyLong_AsUnsignedLongLongMask(myResult);
double result = PyLong_AsDouble(myResult2);
以上的方法都没有成功,当我尝试返回数字119599936时,出现的错误是:
Exception SystemError: '..\\Objects\\longobject.c:739: bad argument to internal
function' in 'garbage collection' ignored
Fatal Python error: unexpected exception during garbage collection
1 个回答
1
你的代码没有进行任何错误检查,而且你也没有提供memory_leak_test
模块的源代码,所以我们很难猜测问题出在哪里。我猜可能是memory_leak_test
没有成功导入,或者memory_leak_test.begin("CacheSetup")
抛出了异常,或者返回了None
,而不是你代码所期待的数字。
为了调试这个问题,可以按照以下建议来重写代码:
检查可能返回错误的Python/C函数的错误信息。每当出现你无法处理的错误时,调用
PyErr_Print()
并终止当前执行(除非你预期会出现这个错误并想要妥善处理,那样的话就调用PyErr_Clear()
)。当你不再需要某些对象时,使用
Py_DECREF
来减少它们的引用计数。这些对象通常是像PyString_FromString
、PyTuple_Pack
和PyObject_CallOject
这样的返回值。学习并使用一些方便的函数,比如
PyObject_CallFunction
、PyObject_CallMethod
和PyImport_ImportModule
,这些函数可以大大减少创建临时字符串和元组的重复代码。找到这些函数的最好方法是查看现有的Python/C源代码,比如Python自带的那些。使用
PyObject_Print()
来打印中间结果,以便调试。
根据以上建议,这里是你代码的一个可能修改版本:
Py_Initialize();
PyObject *module = PyImport_ImportModule("memory_leak_test");
if (!module) {
PyErr_Print();
return;
}
PyObject *result = PyObject_CallMethod(module, "begin", "s", "CacheSetup");
Py_DECREF(module);
if (!result) {
PyErr_Print();
return;
}
printf("got result of type %s\n", Py_TYPE(result)->tp_name);
PyObject_Print(result, stdout, 0);
putchar('\n');
Py_DECREF(result);
Py_Finalize();