美文网首页大数据 爬虫Python AI SqlPython小哥哥
Python的C/C++扩展——用SWIG封装C++为Pytho

Python的C/C++扩展——用SWIG封装C++为Pytho

作者: 14e61d025165 | 来源:发表于2019-03-28 15:36 被阅读1次

    Python调用C/C++代码的利器除了boost_python外,还有SWIG(Simplified Wrapper and Interface Generator),它是用来为脚本语言调用C和C++程序的软件开发工具,它实际上是一个编译器,获取C/C++的声明和定义,用一个壳封装起来,以便其它脚本语言访问这些声明。所以,SWIG 最大的好处就是将脚本语言的开发效率和 C/C++ 的运行效率有机的结合起来。

    image

    前面的文章提到一个C++实现的双数组Trie Tree的实现:cedar,它在中文分词、新词发现等算法中的应用。本文以cedar的SWIG封装实现来说明SWIG的使用。

    0. 安装swig

    工欲善其事必先利其器,首先要安装swig,Ubuntu安装swig很简单:

    <pre class="hljs nginx">sudo aptitude install swig</pre>

    1. 声明和定义C/C++代码

    在cedar的swig目录下面有cedar的C++声明和实现代码trie.h,但是这个实现里面没有遍历所有key的函数方法,所以我添加了一个实现,首先定义一个数据结构来定义key:

    <pre class="prettyprint hljs cpp">// key-value pair return type for next_key()
    class kv_t {
    public:
    std::string key;
    int value;
    };</pre>

    添加一个函数每次返回一个key,当key字符串为空时表示遍历结束,继续调用的话就又从头开始遍历:

    <pre class="prettyprint hljs cpp">// to iterate all keys
    kv_t next_key() const {
    static size_t from = 0, p = 0;
    union { int i; int x; } b;
    char key[256] = {0};
    kv_t kv;
    if(from == 0) {
    b.i = _t->begin(from, p);
    }else{
    b.i = _t->next(from, p);
    }
    if (b.i == trie_t::CEDAR_NO_PATH) {
    kv.key = "";
    kv.value = 0;
    from = 0;
    p = 0;
    return kv;
    }
    _t->suffix(key, p, from);
    kv.key = key;
    kv.value = b.x;
    return kv;
    }</pre>

    2. 编写接口文件.iPython学习群:683380553,有大牛答疑,有资源共享!是一个非常不错的交流基地!欢迎喜欢Python的小伙伴!

    查看cedar.i可以看到SWIG的接口文件的编写规则:

    首先在 %module 后面声明模块名称,这就是Python在import时使用的模块名称;

    在%{ … %}之间包含相关头文件

    在%include 后面可以声明对STL的支持

    最后声明要封装的函数和变量,也可以之间包含头文件: %include “trie.h”

    3. 封装代码

    可以在Makefile里面看到python-bindings:

    <pre class="prettyprint hljs vim">python-bindings:
    swig -Wall -python -builtin -outdir python -c++ cedar.i
    mv -f cedar_wrap.cxx python</pre>

    直接make或者单独运行上面的swig命令,就可以生成cedar.py和cedar_wrap.cxx文件。

    4. 编译生成动态库

    编译生成的cedar_wrap.cxx使用python distutils的setup,可以参考python/setup.py的编写。setup.py的build如下:

    <pre class="hljs vim">python setup.py build</pre>

    就会在当前目录下面创建目录build,下面生成lib.linux-x86_64-2.7/cedar.py 和 _cedar.so

    相关文章

      网友评论

        本文标题:Python的C/C++扩展——用SWIG封装C++为Pytho

        本文链接:https://www.haomeiwen.com/subject/emoqbqtx.html