有人可以向我解释为什么以下Python代码有效吗?
import ctypes
import ctypes.util
boblib = ctypes.cdll.LoadLibrary(ctypes.util.find_library("bob_is_your_uncle"))
boblib.cos.argtypes = [ctypes.c_double]
boblib.cos.restype = ctypes.c_double
print(boblib.cos(0)) # This prints out "1.0"
我1000%确定没有" bob_is_your_uncle"我的文件系统上的库。然而,似乎ctypes加载了m
库。为什么会这样?
另外,如果我这样做:print(boblib)
,我明白了:
<CDLL 'None', handle 7f6a80f6d170 at 0x7f6a7f34d0b8>
CDLL 'None'
是什么意思?
提前致谢。
PS:对我的两个Python解释器执行--version
:
Python 3.6.5rc1
和Python 2.7.14+
。上面的代码在两个版本上都给出了相同的结果。我的操作系统是Debian(测试回购)。
答案 0 :(得分:2)
它没有加载数学库。它似乎正在加载Python可执行文件本身,其中链接有cos
。
确实没有名为bob_is_your_uncle
的库,因此find_library
会返回None
。 (这就是None
来自你所看到的输出的地方。)
在Unix上,LoadLibrary
逻辑有一个specific check,它将None
名称转换为基础dlopen
例程的空指针。 dlopen
的空名称为special handling:
如果 filename 为NULL,则返回的句柄用于主程序。
事实上,在Unix上,ctypes.pythonapi
为created为
pythonapi = PyDLL(None)
首先解释None
处理的原因。您创建的CDLL对象几乎,如ctypes.pythonapi
,除了它没有为函数调用保存GIL或检查异常(因为CDLL而不是PyDLL),所以它没用用于与实际的C Python API交互。