kil*_*les 27 c++ python import namespaces importerror
当我导入我构建的模块时,我得到了与boost-python相关的错误:
Traceback (most recent call last):
File "<string>", line 1, in <module>
ImportError: dlopen(./myMod.so, 2): Symbol not found: __ZN5boost6python7objects15function_objectERKNS1_11py_functionERKSt4pairIPKNS0_6detail7keywordES9_E
Referenced from: ./myMod.so
Expected in: flat namespace
in ./myMod.so
Run Code Online (Sandbox Code Playgroud)
这究竟意味着什么?为什么会出现这个错误?
Shm*_* H. 19
问题是由编译的libc++
对象和编译的对象混合引起的libstdc++
.
在我们的例子中,库myMod.so
(编译libstdc++
)需要boost-python
使用libstdc++
(boost-python-libstdc++
从现在开始)编译.如果boost-python
是boost-python-libstdc++
,它会正常工作.否则 - 在它boost-python
已编译的计算机libc++
(或另一个c ++库)上,加载和运行它会有问题.
在我们的例子中,它发生是因为libc++
开发人员有意改变了所有符号的名称,以防止你(并保存你)混合来自他们库的代码和来自不同代码的代码:myMod.so
需要一个从类型中获取参数的函数.在libc++
,这种类型的名称是std::__1::pair
.因此,未找到此符号.
要理解为什么混合两个版本的相同API是坏的,请考虑这种情况:有两个库:Foo
和Bar
.它们都有一个函数,它接受std::string
并使用它作为某些东西,但它们使用不同的c ++库.当一个std::string
已创建的Foo
将被传递给Bar
,Bar
将认为这是它的c ++库的一个实例,std::string
然后可能发生坏事(它们是完全不同的对象).
注意:在某些情况下,在程序的完全不同的部分中,同一API的两个或更多不同版本没有问题.如果他们将在它们之间传递此API的对象,则会出现问题.但是,检查可能非常困难,特别是如果它们仅将API对象作为另一个对象的成员传递.此外,库的初始化函数可以执行不应发生两次的事情.另一个版本可能再次做这些事情.
您始终可以重新编译库并使它们相互匹配.
您可以将boost-python
库链接到静态库.然后,它几乎可以在每台计算机上运行(即使是未boost-python
安装的计算机).在这里查看更多相关信息.
myMod.so
需要另一个版本boost-python
,一个用特定的c ++库编译的版本.因此,它不适用于任何其他版本.
小智 8
就我而言,我收到:
ImportError: dlopen(/Library/Frameworks/Python.framework/Versions/3.8/lib/python3.8/site-packages/xmlsec.cpython-38-darwin.so, 0x0002): symbol not found in flat namespace '_xmlSecDSigNs'
Run Code Online (Sandbox Code Playgroud)
背景:
M1 MacBook Pro 带蒙特里
我正在使用 python virtualenv (使用 pyenv)来使用早期版本的 python3.8 (3.8.2),而我的系统本机安装了 3.8.10。
当我处于激活的 3.8.2 virtualenv 中时,我注意到 dlopen() 中的路径指向本机 python 安装中的包,而不是 virtualenv 安装中的包。
解决方案:
就我而言,我根本不需要本机 3.8 版本,因此我只需将其删除即可解决问题。
我发现的解决方案之一是使用 no-binary 标志卸载并重新安装它,这会强制 pip 从源代码编译模块,而不是从预编译的 Wheel 安装。
pip install --no-binary :all: <name-of-module>
Run Code Online (Sandbox Code Playgroud)
在这里找到了这个解决方案
归档时间: |
|
查看次数: |
24074 次 |
最近记录: |