关于pybind11pybind11是一个轻量级的“Header-only”库,它向Python公开C++类型,反之亦然。主要用于将已有的C++代码绑定到Python。pybind11的目标和语法都类似于boost.python库。利用编译时自省来推断类型信息。boost.python最大的问题是boost过于复杂和庞大。pybind11去掉注释,代码只有4000多行,需要依赖Python2.7或者Python3。CompilerssupportedClang/LLVM(anynon-ancientversionwithC++11support)GCC4.8ornewerMicrosoftVisualStudio2015ornewerIntelC++compilerv17ornewerStartusingpybind11介绍pybind11的基本特性。为Linux/MacOS编译测试用例,需要安装python-dev或python3-dev,cmake。mkdirbuildcdbuildcmake..makecheck-j4最后一行命令makecheck-j4将编译并自动执行测试用例。Windows仅支持VisualStudio2015及更新版本。mkdirbuildcdbuildcmake..cmake--build。--configRelease--targetcheck上面的命令会创建一个VisualStudio项目,项目会自动编译。注意:如果所有测试都失败,请确保Python二进制类型和编译测试用例的二进制类型与处理器类型相匹配。头文件和命名空间为简洁起见,所有示例都采用以下两行代码:#includenamespacepy=pybind11;某些功能可能需要其他更多头文件,但那些部分会在需要时列出。绑定简单函数让我们首先用一个极其简单的函数创建一个python绑定,该函数将两个数字相加并返回结果intadd(inti,intj){returni+j;}为了简单起见,我们将函数和绑定代码放在一起在文件example.cpp#includenamespacepy=pybind11;intadd(inti,intj){returni+j;}PYBIND11_MODULE(example,m){m.doc()="pybind11示例插件”;//可选模块规范m.def("add",&add,"Afunctionwhichaddstwonumbers");}PYBIND11_MODULE()宏将创建一个函数,当Python发出导入语句时将调用该函数。模块名称“example”,由宏的第一个参数指定(不得出现在引号中)。第二个参数“m”定义了py::module的一个变量。函数py::module::def()生成绑定代码,将add()函数暴露给Python。注意:只需要少量的代码就可以完成C++与Python的绑定,所有关于函数参数和返回值的细节都会由模板元编程自动推导出来!整体方法和语法借鉴自Boost.Python,但底层实现完全不同。pybind11是一个“header-only”库,因此它不需要链接(依赖)任何库,也不需要任何转换步骤。例如,在Linux中,可以使用以下命令直接编译该示例:c++-O3-Wall-shared-std=c++11-fPIC`python3-mpybind11--includes`example.cpp-oexample`python3-config--extension-suffix`有关完整的跨平台说明,请参阅“构建系统”部分以获取详细信息。示例构建完成后,会生成一个可以导入(import)到Python中的二进制模块。编译后的模块位于当前目录中,下面显示了如何在Python会话中使用新生成的模块:importexampleexample.add(1,2)对关键字参数(对于前面的示例)的简单修改将告诉Python参数的名称成为可能(在本例中为“i”和“j”)m.def("add",&add,"Afunctionwhichaddstwonumbers",py::arg("i"),py::arg("j"));py::arg是许多将元数据传递给py::module::def()的特殊标记之一。通过这个简单的修改,我们可以使用“关键字参数”来调用函数。这是多参数场景下更具可读性的解决方案。以下是如何在Python中使用“关键字参数”:importexample#参数的名称也将出现在文档的函数签名中。help(example)example.add(i=1,j=2)也可以使用更短的命名参数表示法:usingnamespacepybind11::literals;m.def("add2",&add,"i"_a,"j"_a);_a后缀是一个C++11字面量,相当于py::arg。默认参数现在假定该函数具有默认参数:intadd(inti=1,intj=2){returni+j;}不幸的是,pybind11无法自动提取这些参数,因为它们(默认参数)不属于函数类型信息。但是,使用py::arg扩展可以轻松实现这些功能。以下示例将显示pybind11对默认参数的支持:PYBIND11_MODULE(example,m){m.doc()="pybind11exampleplugin";//可选模块描述//默认参数m.def("add3",&add,"Afunctionwhichaddstwonumbers",py::arg("i")=1,py::arg("j")=2);}现在在python中使用带有默认参数的add函数:>>>importexample>>>help(example.add3)帮助模块example:add3(...)内置函数add3方法。PyCapsule实例add3(i:int=1,j:int=2)->int一个将两个数相加的函数>>>example.add3()3>>>example.add3(3)5>>>example.add3(j=3)4>>>pybind11中通过py::导出变量module::attr()函数实现了C++向Python导出变量。内置类型和泛型对象在被??指定为属性时会自动转换,函数py::module::cast也可以用来进行显式转换。PYBIND11_MODULE(示例,m){m.attr(“the_answer”)=42;py::objectworld=py::cast("世界");m.attr("what")=world;}以下示例将展示如何在Python中访问导出的变量:>>>importexample>>>example.the_answer42>>>example.what'World'>>>>>>example.the_answer=100>>>example.the_answer100>>>支持的数据类型大量数据类型开箱即用,可以无缝用作函数参数、返回值或py转换::投掷。这部分将在类型转换章节中介绍。