python和C语言混合编程实例


Posted in Python onJune 04, 2014

最近为了测试网速情况怎么样,由于部分业务服务器需要关闭icmp,这样的话采用普通的ping就无法适应我的需求,于是自己简单的写了一个基于tcp端口的ping的程序,由于c执行效率比较的不错,但是开发效率低下,而python是开发效率高,但是执行效率不如C,由于需要大规模的使用,于是用C实现核心部分的代码,并把这部分实现成一个python的模块,由python调用c的模块,下面就贴代码吧

/* tcpportping.c */
#include <Python.h>
#include <string.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <netdb.h>
#include <sys/time.h>/* count time functions */
static double mytime(void)
{
    struct timeval tv;
    if (gettimeofday(&tv, NULL) == -1)
        return 0.0;
    return (double)tv.tv_usec + (double)tv.tv_sec * 1000000;
}
static PyObject *                                 /* returns object */
tcpping(PyObject *self, PyObject *args )
{
    struct  sockaddr_in addr;
    struct  hostent *hp;
    double  time;
    char    *host = NULL;
    int     fd;
    int     port, timeout;
    if (!PyArg_ParseTuple(args, "sii", &host, &port, &timeout))  /* convert Python -> C */
        return NULL;                              /* null=raise exception */
    if ((fd = socket(AF_INET, SOCK_STREAM, 0)) < 0) {
        return Py_BuildValue("d", -1.0);        /* convert C -> Python */
    }
    bzero((char *)&addr, sizeof(addr));
    if ((hp = gethostbyname(host)) == NULL) {
        return Py_BuildValue("d", -2.0);        /* convert C -> Python */
    }
    bcopy(hp->h_addr, &addr.sin_addr, hp->h_length);
    addr.sin_family = AF_INET;
    addr.sin_port = htons(port);
    struct timeval tv;
    tv.tv_sec = 0;
    tv.tv_usec = timeout * 1000;
    double stime = mytime();
    if (connect(fd, (struct sockaddr*)&addr, sizeof(addr)) < 0) {
        return Py_BuildValue("d", -3.0);        /* convert C -> Python */
    }
    fd_set read, write;
    FD_ZERO(&read);
    FD_ZERO(&write);
    FD_SET(fd, &read);
    FD_SET(fd, &write);
    if (select(fd + 1, &read, &write, NULL, &tv) == 0) {
        close(fd);
        return Py_BuildValue("d", -4.0);        /* convert C -> Python */
    }
    double etime = mytime();
    time = etime - stime;
    if (!FD_ISSET(fd, &read) && !FD_ISSET(fd, &write)) {
        close(fd);
        return Py_BuildValue("d", -4.0);        /* convert C -> Python */
    }
    close(fd);
    return Py_BuildValue("d", time/1000);        /* convert C -> Python */
}
/* registration table  */
static struct PyMethodDef portping_methods[] = {
    {"tcpping", tcpping, METH_VARARGS},       /* method name, C func ptr, always-tuple */
    {NULL, NULL}                   /* end of table marker */
};
/* module initializer */
void inittcpportping( )                       /* called on first import */
{                                      /* name matters if loaded dynamically */
    (void) Py_InitModule("tcpportping", portping_methods);   /* mod name, table ptr */
}

编译成python模块

gcc tcpportping.c  -I/usr/include/python2.4 -shared -L/usr/bin -fpic -lpython2.4 -o tcpportping.so

下面是python调用c模块的代码:

#!/usr/bin/env pythonimport tcpportping
import time
i = 0
while i < 5:
    t = tcpportping.tcpping('www.baidu.com', 80, 1000)
    if t < 0:
        print "time out"
    else:
        print t
    time.sleep(0.5)
    i += 1

执行python代码就可以实现端口ping的结果,从测试的情况来看,该程序执行的结果跟普通的ping几乎没有什么差别。
Python 相关文章推荐
python快速排序代码实例
Nov 21 Python
python元组操作实例解析
Sep 23 Python
让代码变得更易维护的7个Python库
Oct 09 Python
python: 判断tuple、list、dict是否为空的方法
Oct 22 Python
将pandas.dataframe的数据写入到文件中的方法
Dec 07 Python
python使用pdfminer解析pdf文件的方法示例
Dec 20 Python
Python绘制频率分布直方图的示例
Jul 08 Python
Python random模块制作简易的四位数验证码
Feb 01 Python
windows下python安装pip方法详解
Feb 10 Python
浅谈spring boot 集成 log4j 解决与logback冲突的问题
Feb 20 Python
python利用datetime模块计算程序运行时间问题
Feb 20 Python
把Anaconda中的环境导入到Pycharm里面的方法步骤
Oct 30 Python
python实现的一个p2p文件传输实例
Jun 04 #Python
python实现文件分组复制到不同目录的例子
Jun 04 #Python
python实现的udp协议Server和Client代码实例
Jun 04 #Python
Python实现同时兼容老版和新版Socket协议的一个简单WebSocket服务器
Jun 04 #Python
Python程序员鲜为人知但你应该知道的17个问题
Jun 04 #Python
Python和Ruby中each循环引用变量问题(一个隐秘BUG?)
Jun 04 #Python
python控制台英汉汉英电子词典
Apr 23 #Python
You might like
php通过获取头信息判断图片类型的方法
2015/06/26 PHP
Yii2搭建后台并实现rbac权限控制完整实例教程
2016/04/28 PHP
PHP实现的简单排列组合算法应用示例
2017/06/20 PHP
自己开发Dojo的建议框架
2008/09/24 Javascript
Prototype 学习 工具函数学习($A方法)
2009/07/12 Javascript
浅析jQuery中调用ajax方法时在不同浏览器中遇到的问题
2014/06/11 Javascript
javascript函数中参数传递问题示例探讨
2014/07/31 Javascript
jquery操作 iframe的方法
2014/12/03 Javascript
详解JavaScript ES6中的Generator
2015/07/28 Javascript
JS基于构造函数实现的菜单滑动显隐效果【测试可用】
2016/06/21 Javascript
卸载安装Node.js与npm过程详解
2016/08/15 Javascript
Nodejs中解决cluster模块的多进程如何共享数据问题
2016/11/10 NodeJs
详解nodejs微信公众号开发——6.自定义菜单
2017/04/13 NodeJs
Ajax高级笔记 JavaScript高级程序设计笔记
2017/06/22 Javascript
React-Native使用Mobx实现购物车功能
2017/09/14 Javascript
jQuery的Ajax接收java返回数据方法
2018/08/11 jQuery
Vue中的基础过渡动画及实现原理解析
2018/12/04 Javascript
vue 实现基础组件的自动化全局注册
2020/12/25 Vue.js
[02:35]DOTA2英雄基础教程 末日使者
2013/12/04 DOTA
python检查序列seq是否含有aset中项的方法
2015/06/30 Python
python中实现指定时间调用函数示例代码
2017/09/08 Python
对python3 urllib包与http包的使用详解
2018/05/10 Python
Python3爬虫中pyspider的安装步骤
2020/07/29 Python
python 实现简易的记事本
2020/11/30 Python
使用html2canvas.js实现页面截图并显示或上传的示例代码
2018/12/18 HTML / CSS
米兰网婚纱礼服法国网上商店:Milanoo法国
2016/08/20 全球购物
高中美术教学反思
2014/01/19 职场文书
yy生日主持词
2014/03/20 职场文书
共筑中国梦演讲稿
2014/04/23 职场文书
教师党的群众路线教育实践活动剖析材料
2014/10/09 职场文书
入党介绍人意见2015
2015/06/01 职场文书
童年读书笔记
2015/06/26 职场文书
python实现简易自习室座位预约系统
2021/06/30 Python
nginx安装以及配置的详细过程记录
2021/09/15 Servers
详解redis在微服务领域的贡献
2021/10/16 Redis
python index() 与 rindex() 方法的使用示例详解
2022/12/24 Python