MingW编译Python拓展与Cython
这篇文章主要是针对不想用MSBuild编译Python拓展的童鞋(VS巨无霸虽然牛逼,但是无奈太大,安装又慢),我将不使用setup.py这样的编译方式,而使用原生gcc编译(实际上使用makefile,反正没差别)
纯手工写一个朴素的C拓展
// calc.c
#include
int add(int x, int y){ // C 函数
return x + y;
}
static PyObject *calc_add(PyObject *self, PyObject *args){
int x, y;
// Python传入参数
// "ii" 表示传入参数为2个int型参数,将其解析到x, y变量中
if(!PyArg_ParseTuple(args, "ii", &x, &y))
return NULL;
return PyLong_FromLong(add(x, y));
}
// 模块的方法列表
static PyMethodDef CalcMethods[] = {
{"add", calc_add, METH_VARARGS, "函数描述"},
{NULL, NULL, 0, NULL}
};
// 模块
static struct PyModuleDef calcmodule = {
PyModuleDef_HEAD_INIT,
"calc", // 模块名
NULL, // 模块文档
-1, /* size of per-interpreter state of the module,
or -1 if the module keeps state in global variables. */
CalcMethods
};
// 初始化
PyMODINIT_FUNC PyInit_calc(void)
{
return PyModule_Create(&calcmodule);
}
Makefile
# PYTHONPATH 换成自己的python地址
PYTHONPATH = D:/py38
INC = $(PYTHONPATH)/include
LIBS = $(PYTHONPATH)/libs
LIB = python38
calc.pyd: calc.o
gcc -shared -o calc.pyd calc.o -L $(LIBS) -l $(LIB)
calc.o: calc.c
gcc -o calc.o -c calc.c -I $(INC)
.PHONY: clean
clean:
rm -rf *.pyd *.o
编译
make
测试
# test.py
import calc
print(calc.add(12, 34))
正常输出46,很完美!
MingW编译Cython代码
# hello.pyx
# 对外可见Python函数
def padd(x, y):
return x + y
# 对外不可见C函数
cdef int cadd(int x, int y):
return x + y
# 对外可见C函数
cpdef int cpadd(int x, int y):
return x + y
Makefile
# 这里换成你自己的Python目录
PYTHONPATH = D:/py38
INC = $(PYTHONPATH)/include
LIBS = $(PYTHONPATH)/libs
LIB = python38
hello.pyd: hello.o
gcc -shared -o hello.pyd hello.o -L $(LIBS) -l $(LIB)
hello.o: hello.c
gcc -DMS_WIN64 -o hello.o -c hello.c -I $(INC)
hello.c: hello.pyx
cython -3 hello.pyx -o hello.c
.PHONY: clean
clean:
rm -rf *.pyd *.o *.c
编译
make
测试
# test.py
import hello
print(hello.padd(12, 34))
print(hello.cpadd(12, 89))
如果编译正确,这里可以正常输出结果!