我无法使用 Visual Studio 将 python.dll 构建为静态库 (/MTd)

Posted

技术标签:

【中文标题】我无法使用 Visual Studio 将 python.dll 构建为静态库 (/MTd)【英文标题】:I cannot build python.dll as a static library (/MTd) using Visual Studio 【发布时间】:2018-01-31 15:03:04 【问题描述】:

我正在使用 Python 的 3.6.4 源代码版本。我可以使用 Visual Studio 作为动态库 (/MDd) 轻松构建它。我可以将 Python .dll 链接到我自己的代码并验证其操作。

但是当我使用 (/MTd) 构建它(和我的代码)时,当我尝试使用 Python 程序打开一个文件时,它很快就会脱轨。 read.cpp ("Expression: _osfile(fh) & FOPEN") 中的调试断言失败。我认为正在发生的是 Python .dll 与不正确的系统库链接。我不知道如何让它与正确的链接(静态库)。

【问题讨论】:

这是一个断言,而不是run off the rails。这并不意味着存在任何链接错误 - 如果存在链接错误,您将无法使用任何一个库,更不用说在其中执行断言了。这意味着代码正在尝试从已关闭的文件中读取它是using file functions on socket handles。在 Windows 中,套接字不是文件。你想建立什么来源?您是否检查过适用于 Windows 的 Python 二进制文件是如何构建的?有些东西告诉我他们使用不同的功能 如果使用 /MDd 构建,我的代码可以正常工作。 embeddable python.dll 也可以使用,可以在 python.org 下载。可能发生的情况是您链接到一个使用文件函数而不是套接字函数的库。 VS 为 C++ 提供了比 C 更好的支持 - 它是 C++ 的最佳编译器之一,而 C 在 VS 2017 年之前基本上被放弃了。也许你会在 VS 中获得更好的运气2017. 我会先检查 Windows 的构建说明。 提示:“该解决方案没有静态库配置。但是,构建静态库而不是 DLL 很容易。您只需将“配置类型”设置为“静态库( .lib)”并将预处理器宏“Py_ENABLE_SHARED”更改为“Py_NO_ENABLE_SHARED”。您可能还必须将“运行时库”从“多线程 DLL (/MD)”更改为“多线程 (/MT)”。 " 【参考方案1】:

这是我构建和使用静态嵌入到另一个应用程序中的 python 所需要做的。

构建静态python库(例如python36_d.lib、python36.lib)

    将 python 解决方案 (pcbuild.sln) 中的所有项目转换为静态。这是大约 40 个项目,因此可能需要一段时间。这包括将要构建的库产品设置为“静态库”,并将所有 /MD 和 /MDd 构建选项设置为 /MT 和 /MTd。

    至少对于 pythoncore 项目,将预处理定义更改为 Py_NO_ENABLE_SHARED。这告诉项目它将寻找来自静态库的调用。

    不择手段,为自己找到一个 pyconfig.h 文件并将其放入 Python 构建的包含区域。目前尚不清楚该文件是如何从 Windows 工具构建的,但似乎可以从其他来源获取一个,并且工作正常。人们可能会从您正在构建的代码的预编译版本中获取 pyconfig.h。 [顺便说一句,我构建的 Python 是 3.6.5,是用 Windows 2015 构建的,更新 3。]

希望这能让您同时构建 python36.lib 和 python36_d.lib。现在您需要对您的应用程序项目进行更改,以使其能够与 python 库链接。你需要这样做:

    将 Python Include 目录添加到 General->Include Directories 列表中。 将 Python 库目录添加到“常规”->“库目录”列表中。 这将是 ..\PCBuild\win32 和 ..\PCBuild\amd64。 将定义 Py_NO_ENABLE_SHARED 添加到 C/C++ -> 预处理器区域。 对于链接器->输入添加(对于发行版)python36.lib;shlwapi.lib;version.lib 和(对于调试)python36_d.lib;shlwapi.lib;version.lib。

应该就是这样。它应该运行并工作。但还有一件事。为了能够正常运行,可执行文件需要访问 python 构建的 Lib 目录。因此,需要将其副本移动到可执行文件(包含嵌入式 python)所在的任何位置。或者您可以将 Lib 区域添加到 windows 的执行路径中。这应该也可以。

这就是全部。

【讨论】:

这一切都有一个缺点。 Python 模块系统依赖于动态库,因此,如果您让这一切顺利进行,您将无法导入具有需要加载的 .dll 关联的模块。见:***.com/questions/19560594/…

以上是关于我无法使用 Visual Studio 将 python.dll 构建为静态库 (/MTd)的主要内容,如果未能解决你的问题,请参考以下文章

无法将 Visual Studio 代码连接到 PHP

Visual Studio 2017 无法使用库构建

无法将 GitLab 与 Visual Studio Code 连接

Visual Studio Code:无法将 ESLint 修复应用于文档

Visual Studio:无法将ATL类添加到ATL项目中?

在Visual Studio中构建的代码将无法在TFS中生成