Cythonized Python.Net 代码找不到系统程序集



当我使用 Cython 编译使用 Python.NET 访问 .NET 程序集的 Python 代码时,它找不到这些程序集:

ModuleNotFoundError: No module named 'System'

无需编译即可正常工作。

对于演示代码,我使用了 https://github.com/pythonnet/pythonnet/blob/master/demo/helloform.py

我的setup.py文件:

from distutils.core import setup
from distutils.extension import Extension
from Cython.Build import cythonize
ext_modules = [
Extension(
'helloform',
sources = ['helloform.py'],
language = 'c++'
)
]
setup(
name = 'helloform',
ext_modules = cythonize(ext_modules),
)

然后我用python setup.py build_ext --inplace构建它.

我想用import helloform从 Python 提示符加载编译的模块,但它失败了

Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "helloform.py", line 8, in init helloform
ModuleNotFoundError: No module named 'System'

这个答案未经测试——我认为我不能轻易地设置一个环境来测试,所以这只是一个猜测。如果它不起作用,我会删除它。

这可能是一个错误,如果您希望长期修复它,您应该报告它。Cython确实尽可能尝试与Python兼容。快速调查表明,Python.NET 会覆盖内置的__import__函数。Cython 希望在 Python 2 中查找并使用此函数,但在 Python 3 中则不然。这不再是自定义导入行为的首选方法(但仍受支持)。我猜它会在 Cython + Python 2 中工作吗?

作为一种解决方法,您可能应该只在 Python 中运行导入语句。有两种明显的方法可以做到这一点:

  1. 编写一个只包含导入语句的单独小模块,然后在 Cython 中从该模块导入:

    from import_module import WinForms, Size, Point
    
  2. 运行exec中的导入语句;从您传递给它的全局字典中提取值:

    import_dict = {}
    exec("""import clr
    # etc...
    """, import_dict) # pass a dict in as `globals`
    WinForms = import_dict['WinForms']
    # etc.
    

最新更新