python与C、C++混编的四种方式(小结)


Posted in Python onJuly 15, 2019

混编的含义有两种,

一种是在python里面写C

一种是C里面写python

本文主要是进行简化,方便使用。

#####################################################################################################

第一种、Python调用C动态链接库(利用ctypes)

pycall.c

/***gcc -o libpycall.so -shared -fPIC pycall.c*/ 
#include <stdio.h> 
#include <stdlib.h> 
int foo(int a, int b) 
{ 
 printf("you input %d and %d\n", a, b); 
 return a+b; 
}

pycall.py

import ctypes 
ll = ctypes.cdll.LoadLibrary  
lib = ll("./libpycall.so")  
lib.foo(1, 3) 
print '***finish***'

运行方法:

gcc -o libpycall.so -shared -fPIC pycall.c
python pycall.py

第2种、Python调用C++(类)动态链接库(利用ctypes)

pycallclass.cpp

#include <iostream> 
using namespace std; 
 
class TestLib 
{ 
  public: 
    void display(); 
    void display(int a); 
}; 
void TestLib::display() { 
  cout<<"First display"<<endl; 
} 
 
void TestLib::display(int a) { 
  cout<<"Second display:"<<a<<endl; 
} 
extern "C" { 
  TestLib obj; 
  void display() { 
    obj.display();  
   } 
  void display_int() { 
    obj.display(2);  
   } 
}

pycallclass.py

import ctypes 
so = ctypes.cdll.LoadLibrary  
lib = so("./libpycallclass.so")  
print 'display()' 
lib.display() 
print 'display(100)' 
lib.display_int(100)

运行方法:

g++ -o libpycallclass.so -shared -fPIC pycallclass.cpp
python pycallclass.py

第3种、Python调用C和C++可执行程序

main.cpp

#include <iostream> 
using namespace std; 
int test() 
{ 
  int a = 10, b = 5; 
  return a+b; 
} 
int main() 
{ 
  cout<<"---begin---"<<endl; 
  int num = test(); 
  cout<<"num="<<num<<endl; 
  cout<<"---end---"<<endl; 
}

main.py

import commands 
import os 
main = "./testmain" 
if os.path.exists(main): 
  rc, out = commands.getstatusoutput(main) 
  print 'rc = %d, \nout = %s' % (rc, out) 
 
print '*'*10 
f = os.popen(main)  
data = f.readlines()  
f.close()  
print data 
 
print '*'*10 
os.system(main)

运行方法(只有这种不是生成.so然后让python文件来调用):

g++ -o testmain main.cpp
python main.py

第4种、扩展Python(C++为Python编写扩展模块)(超级麻烦的一种)

Extest2.c

#include <stdio.h> 
#include <stdlib.h> 
#include <string.h> 
 
int fac(int n) 
{ 
  if (n < 2) return(1); 
  return (n)*fac(n-1); 
} 
 
char *reverse(char *s) 
{ 
  register char t, 
      *p = s, 
      *q = (s + (strlen(s) - 1)); 
 
  while (s && (p < q)) 
  { 
    t = *p; 
    *p++ = *q; 
    *q-- = t; 
  } 
  return(s); 
} 
 
int test() 
{ 
  char s[BUFSIZ]; 
  printf("4! == %d\n", fac(4)); 
  printf("8! == %d\n", fac(8)); 
  printf("12! == %d\n", fac(12)); 
  strcpy(s, "abcdef"); 
  printf("reversing 'abcdef', we get '%s'\n", \ 
    reverse(s)); 
  strcpy(s, "madam"); 
  printf("reversing 'madam', we get '%s'\n", \ 
    reverse(s)); 
  return 0; 
} 
 
#include "Python.h" 
 
static PyObject * 
Extest_fac(PyObject *self, PyObject *args) 
{ 
  int num; 
  if (!PyArg_ParseTuple(args, "i", &num)) 
    return NULL; 
  return (PyObject*)Py_BuildValue("i", fac(num)); 
} 
 
static PyObject * 
Extest_doppel(PyObject *self, PyObject *args) 
{ 
  char *orig_str; 
  char *dupe_str; 
  PyObject* retval; 
 
  if (!PyArg_ParseTuple(args, "s", &orig_str)) 
    return NULL; 
  retval = (PyObject*)Py_BuildValue("ss", orig_str, 
    dupe_str=reverse(strdup(orig_str))); 
  free(dupe_str);       
  return retval; 
} 
 
static PyObject * 
Extest_test(PyObject *self, PyObject *args) 
{ 
  test(); 
  return (PyObject*)Py_BuildValue(""); 
} 
 
static PyMethodDef 
ExtestMethods[] = 
{ 
  { "fac", Extest_fac, METH_VARARGS }, 
  { "doppel", Extest_doppel, METH_VARARGS }, 
  { "test", Extest_test, METH_VARARGS }, 
  { NULL, NULL }, 
}; 
 
void initExtest() 
{ 
  Py_InitModule("Extest", ExtestMethods); 
}

setup.py

#!/usr/bin/env python 
 
from distutils.core import setup, Extension 
 
MOD = 'Extest' 
setup(name=MOD, ext_modules=[Extension(MOD, sources=['Extest2.c'])])

运行方法:

python setup.py build
cd build/lib.linux-x86_64-2.7

进入python交互模式>>>

import Extest
Extest.test()

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Python 相关文章推荐
Python 操作文件的基本方法总结
Aug 10 Python
git进行版本控制心得详谈
Dec 10 Python
Python3 queue队列模块详细介绍
Jan 05 Python
用python实现的线程池实例代码
Jan 06 Python
PyQt5每天必学之像素图控件QPixmap
Apr 19 Python
TensorFlow的权值更新方法
Jun 14 Python
python实现AES加密解密
Mar 28 Python
python学习——内置函数、数据结构、标准库的技巧(推荐)
Apr 18 Python
Python @property装饰器原理解析
Jan 22 Python
如何使用Python自动生成报表并以邮件发送
Oct 15 Python
利用Python判断你的密码难度等级
Jun 02 Python
Python使用华为API为图像设置多个锚点标签
Apr 12 Python
解决Python3 控制台输出InsecureRequestWarning问题
Jul 15 #Python
python导包的几种方法(自定义包的生成以及导入详解)
Jul 15 #Python
Python将文字转成语音并读出来的实例详解
Jul 15 #Python
解决win7操作系统Python3.7.1安装后启动提示缺少.dll文件问题
Jul 15 #Python
Python符号计算之实现函数极限的方法
Jul 15 #Python
在python 中split()使用多符号分割的例子
Jul 15 #Python
Python-Seaborn热图绘制的实现方法
Jul 15 #Python
You might like
一个odbc连mssql分页的类
2006/10/09 PHP
Laravel 5框架学习之表单验证
2015/04/08 PHP
PHP下载文件的函数实例代码
2016/05/18 PHP
PHP面向对象程序设计中的self、static、parent关键字用法分析
2019/08/14 PHP
js实现快速分享功能(你的文章分享工具)
2013/06/25 Javascript
Js中使用hasOwnProperty方法检索ajax响应对象的例子
2014/12/08 Javascript
jqueryUI里拖拽排序示例分析
2015/02/26 Javascript
JavaScript必知必会(十) call apply bind的用法说明
2016/06/08 Javascript
详解springmvc 接收json对象的两种方式
2016/12/06 Javascript
Node.js数据库操作之连接MySQL数据库(一)
2017/03/04 Javascript
nodejs中art-template模板语法的引入及冲突解决方案
2017/11/07 NodeJs
nodejs调取微信收货地址的方法
2017/12/20 NodeJs
javascript实现图片轮播代码
2019/07/09 Javascript
js回调函数仿360开机
2019/12/26 Javascript
Vue-axios-post数据后端接不到问题解决
2020/01/09 Javascript
Vue中通过属性绑定为元素绑定style行内样式的实例代码
2020/04/30 Javascript
JS实现放大镜效果
2020/09/21 Javascript
[02:57]DOTA2英雄基础教程 风行者
2014/01/16 DOTA
[01:06]欢迎来到上海,TI9
2018/08/26 DOTA
Python实现Linux的find命令实例分享
2017/06/04 Python
python matlibplot绘制多条曲线图
2021/02/19 Python
python 实现将txt文件多行合并为一行并将中间的空格去掉方法
2018/12/20 Python
python3爬虫怎样构建请求header
2018/12/23 Python
Django数据库连接丢失问题的解决方法
2018/12/29 Python
Python爬虫之UserAgent的使用实例
2019/02/21 Python
python、PyTorch图像读取与numpy转换实例
2020/01/13 Python
Python logging模块handlers用法详解
2020/08/14 Python
大学生先进事迹材料
2014/02/16 职场文书
集体婚礼策划方案
2014/02/22 职场文书
党支部承诺书范文
2014/03/28 职场文书
大一新生期末自我评价
2014/09/12 职场文书
工资收入证明样本(5篇)
2014/09/16 职场文书
家长通知书家长意见
2014/12/30 职场文书
职称评定个人总结
2015/03/05 职场文书
毕业实习单位意见
2015/06/04 职场文书
环境卫生标语
2015/08/03 职场文书