如何在 Windows GUI 应用程序中将嵌入式 Python 连接到控制台的 I/O?
Posted
技术标签:
【中文标题】如何在 Windows GUI 应用程序中将嵌入式 Python 连接到控制台的 I/O?【英文标题】:How can I connect embedded Python to the console's I/O in a Windows GUI app? 【发布时间】:2014-08-06 21:27:03 【问题描述】:我正在 Microsoft Visual Studio 2010 中使用 C++ 制作一个 Windows GUI 应用程序。我想包含一个可以通过该应用程序打开的 Python 调试控制台。我已经按照this answer将C++标准I/O连接到控制台,但是当我随后嵌入Python时,Python似乎无法通过其标准I/O访问控制台:
create_console(); // essentially the function in the answer I linked to above
Py_Initialize(); // initialize Python
printf("hello, world\n"); // works
PyRun_SimpleString("print \"hello, world\""); // does not work
我尝试使用以下方法对此进行修补:
PyObject *py_stdin = PyFile_FromFile(stdin, "<stdin>", "r", NULL);
PySys_SetObject("stdin", py_stdin);
Py_DECREF(py_stdin); py_stdin = NULL;
PyObject *py_stdout = PyFile_FromFile(stdout, "<stdout>", "w", NULL); // *
PySys_SetObject("stdout", py_stdout);
Py_DECREF(py_stdout); py_stdout = NULL;
PyObject *py_stderr = PyFile_FromFile(stderr, "<stderr>", "w", NULL); // *
PySys_SetObject("stderr", py_stderr);
Py_DECREF(py_stderr); py_stderr = NULL;
但上面标有星号 (*) 的行不仅会导致运行时错误(错误消息无非是“Microsoft Visual Studio C 运行时库在 [APP_NAME].exe 中检测到致命错误。”) ,但是 Python 的标准输入仍然不起作用,即使上面的输入块运行没有错误。
【问题讨论】:
尝试嵌入什么版本的 Python? 【参考方案1】:您的程序需要使用与您尝试嵌入的 Python 版本相同的 Microsoft C 运行时 DLL。 Python 2.7 使用 Visual Studio 2008 编译,并在您使用 Visual Studio 2010 和 MSVCRT100.DLL
时使用 MSVCRT90.DLL
。每个 DLL 都有自己的stdin
、stdout
和stderr
,这就是为什么你的create_console
函数无效的原因。这两个 DLL 还具有不同的 FILE *
流内部布局,这就是为什么当您将使用 MSVCRT100.DLL
创建的 FILE *
流传递给 Python 时它会崩溃。它最终尝试将它与MSVCRT90.DLL
一起使用。
基本上要解决这个问题,您需要使用 Visual Studio 2008 编译您的应用程序。
【讨论】:
还有其他解决方法吗?或者是否有可能获得使用MSVCR100.DLL
的 Python 2.7 构建(甚至自己编译一个)?
相反,这会解决我的问题吗:p-nand-q.com/python/building-python-27-with-vs2010.html ?
是的,您可以使用 Visual Studio 2010 构建您自己的 Python 2.7 版本。此处提供了其他可能的解决方法:***.com/a/24714436/3826372 第一个解决方法不适用于您的情况。
我还应该补充一点,这适用于您可能使用的任何第三方 Python 扩展模块。如果你重新编译 Python,你需要用 VS 2010 重新编译那些。
幸运的是我不需要任何扩展(当然除了我自己的)。无论如何,我链接到的构建包含许多第三方扩展。以上是关于如何在 Windows GUI 应用程序中将嵌入式 Python 连接到控制台的 I/O?的主要内容,如果未能解决你的问题,请参考以下文章
如何在 Spring Boot 应用程序中将用户添加到嵌入式 tomcat?