用c++扩展python(一)简单实现

借助官方的说明文档:

https://docs.python.org/2/extending/index.html

https://docs.python.org/zh-cn/3.8/extending/extending.html

 

我们的目标是实现一个Extend的模块,模块中有一个add函数,:

import Exten

print(Exten(1,2))

1.C++文件编写

通过生成一个如下的Extend.cpp文件:

#include "Python.h"

int add(int a, int b){
        return a + b;
}

/* 函数调用*/
static PyObject *Exten_add(PyObject *self, PyObject *args){
        int a,b;

        if(!PyArg_ParseTuple(args, "ii", &a, &b)){
                return NULL;
        }
        //如果所有参数都具有正确的c的相应类型,并且其参数存储在传递其地址的变量中。PyArg_ParseTuple>返回true
        return (PyObject *)Py_BuildValue("i",add(a,b));
        // "i"表示传参类型为int
        //如果没有返回值的话,c返回void应变成python的none,改成以下语句:
        //Py_INCREF(Py_None);return Py_None;
}
/*定义调用的函数名*/
static PyMethodDef ExtenMethods[]={
        {"add", Exten_add, METH_VARARGS},
        {NULL, NULL}
        /*{"add"是python中使用的名字,函数,METH_VARARGS是给解释器C的标识}*/   
};
static struct PyModuleDef ExtenModule = {
        PyModuleDef_HEAD_INIT,
        "Exten",     /* m_name*/
        NULL,        /* m_doc*/
        -1,                  /* m_size*/
        ExtenMethods /* m_methods*/
};

/* 初始化模>块 PyInit_name*/
PyMODINIT_FUNC
PyInit_Exten(){
        PyObject *m = NULL;
        m = PyModule_Create(&ExtenModule);
        //m = Py_InitModule("spam", SpamMethods);
        if(m == NULL)
                return NULL;
}

在传参时注意python中和C中对象的转换。

 

https://docs.python.org/2/c-api/index.html

 

2.创建扩展模块

使用扩展前:需要(1)编译,(2)与Python系统链接

我们可以选择两种方法来进行扩展:

1.将 C++ 语言程序编译成一个扩展模块,生成扩展文件,linux下是.so,windows下是.dll,

需要指定 Python.h 头文件所在的路径,和链接 python2.7 等库文件(-lpython2.7),例外需加上指令 -fPIC -shared 以指导其编译成一个动态链接库。编译使用类似下面的命令(注意将其中的头文件路径改成你的系统中实际的路径)

gcc -I/public/home/yinghuang/software/anaconda3/include/python3.8  -o Exten.so Exten.cpp -fPIC -shared -lpthread -ldl -lutil -lm

获取Python.h头文件,可以在命令行中输入以下命令获得:

$ python -c "import sysconfig; print( sysconfig.get_path('include') )"

 

2.通过Distutils在Python环境中构建和安装模块

在同一目录下建立setup.py

from distutils.core import setup,Extension

MOD = 'Exten' #模块名
setup(name=MOD,ext_modules=[Extension(MOD,sources=['Exten.cpp'])])

在命令行中输入: 

python setup.py build
python setup.py install

这样就可以将模块安装成功了。

 

参考链接:

https://www.jianshu.com/p/558d4f3e4bfb

https://www.jianshu.com/p/eb2618067eae

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章