2017-10-08 139 views
0

old question关于如何捕捉蟒蛇的stdout在C++代码,there is a good answer和它的作品 - 但只有在Python 2如何捕捉Python 3的标准输出在C++代码

我想用类似的东西与Python 3.任何人都可以帮助我吗?

UPDATE

我使用的代码如下。它被从上面引用的Mark回答中移除,唯一的变化是使用PyBytes_AsString而不是PyString_AsString,因为cited in documentation

#include <Python.h> 
#include <string> 

int main(int argc, char** argv) 
{ 
std::string stdOutErr = 
"import sys\n\ 
class CatchOutErr:\n\ 
    def __init__(self):\n\ 
     self.value = ''\n\ 
    def write(self, txt):\n\ 
     self.value += txt\n\ 
catchOutErr = CatchOutErr()\n\ 
sys.stdout = catchOutErr\n\ 
sys.stderr = catchOutErr\n\ 
"; //this is python code to redirect stdouts/stderr 

Py_Initialize(); 
PyObject *pModule = PyImport_AddModule("__main__"); //create main module 
PyRun_SimpleString(stdOutErr.c_str()); //invoke code to redirect 
PyRun_SimpleString("print(1+1)"); //this is ok stdout 
PyRun_SimpleString("1+a"); //this creates an error 
PyObject *catcher = PyObject_GetAttrString(pModule,"catchOutErr"); //get our catchOutErr created above 
PyErr_Print(); //make python print any errors 

PyObject *output = PyObject_GetAttrString(catcher,"value"); //get the stdout and stderr from our catchOutErr object 

printf("Here's the output:\n %s", PyBytes_AsString(output)); //it's not in our C++ portion 

Py_Finalize(); 


return 0; 
} 

我建立它使用Python 3库:

g++ -I/usr/include/python3.6m -Wall -Werror -fpic code.cpp -lpython3.6m

,输出是:

Here's the output: (null)

如果有人需要有关问题的更多信息,请让我知道,我会尝试在这里提供。

+0

以何种方式不行? Python 3的纯Python版本可以很好地适用于Python 3,所以我不明白为什么C-API版本不会? – DavidW

+0

我将编辑问题并放入我正在使用的代码。 – user2540800

+0

'stdOutErr'中的缩进看起来不正确。这将是我的第一个猜测 – DavidW

回答

0

你的问题是,.value不是bytes对象,它是一个string(即Python2 unicode)对象。因此PyBytes_AsString失败。我们可以用PyUnicode_AsEncodedString将它转换为bytes对象。

PyObject *output = PyObject_GetAttrString(catcher,"value"); //get the stdout and stderr from our catchOutErr 
PyObject* encoded = PyUnicode_AsEncodedString(output,"utf-8","strict"); 
printf("Here's the output:\n %s", PyBytes_AsString(encoded)); 

请注意,您应该检查这些结果PyObject*对NULL,看看是否出现了错误。

+0

感谢DavidW,您的提示用上面的代码解决了问题。我还有其他疑问,在我工作的代码中,''PyUnicode_AsEncodedString'总是返回'NULL'。其他函数正在工作(或者至少它们不返回'NULL')。你知道它会是什么吗? – user2540800

+0

这意味着它引发了一个例外。你应该检查检查,找出发生了什么问题。自从您重定向标准错误以来,这有点困难。有可能除了“严格”​​以外的争论可能会使其工作。 – DavidW