Python调用ctypes使用C函数printf的方法


Posted in Python onAugust 23, 2017

在Python程序中导入ctypes模块,载入动态链接库。动态链接库有三种:cdll以及windows下的windll和oledll,cdll载入导出函数使用标准的cdecl调用规范的库,而windll载入导出函数符合stdcall调用规范(Win32 API的原生约定)的库,oledll也使用stdcall调用规范,并假设函数返回Windows的HRESULT错误代码。错误代码用于在出错时自动抛出WindowsError这个Python异常,可以使用COM函数得到具体的错误信息。

使用cdll.msvcrt即可调用MS标准的C库msvcrt,msvcrt包含了大部分标准C函数。

下面来看一下简单的printf函数。

from ctypes import *
msvcrt = cdll.msvcrt
str = "Huanhuan!"
msvcrt.printf("Hello %s\n", str)

这样就可以使用C语言中的printf函数进行输出。
如果在IDLE里运行的话会发现程序没有任何输出结果,这是因为printf是打印到真实的标准输出,而不是sys.stdout。如果想要看到运行结果,可以在CMD里运行python test.py来查看结果,前提是已经设置好了Python的环境变量。或者有一个曲线方法可以在IDLE中显示输出结果,请曲线阅读到文章最后。

如果使用的是Py3K,在控制台里会看到只有开头字符H被输出了。因为Py3K使用的是Unicode编码,而printf不支持该编码,所以需要转码。整理出来三种改写方法可以解决这一问题。

# A 转为byte类型 在字符串前面加b
from ctypes import *
msvcrt = cdll.msvcrt
str = b"Huanhuan!"
msvcrt.printf(b"Hello %s\n", str)

# B 使用wprintf宽字符显示
from ctypes import *
msvcrt = cdll.msvcrt
str = "Huanhuan!"
msvcrt.wprintf("Hello %s\n", str)

# C 转码为utf-8
from ctypes import *
msvcrt = cdll.msvcrt
str = "Huanhuan!"
result = "Hello " + str + "\n"
result = result.encode("utf-8")
msvcrt.printf(result)

最后来搞定在IDLE中曲线显示输出结果的方法。

from ctypes import *
msvcrt = cdll.msvcrt
str = b"Huanhuan!"
s = create_string_buffer(100)  # 必须足够长
msvcrt.sprintf(s, b'Hello %s\n', str)
print(s.value.decode('utf-8'))

先使用sprintf函数把结果输出到s变量,然后再用Python自带的print方法输出s的value。

好了,通过以上的各种方法就可以解决Py3K调用C函数printf的问题了。

什么?你问我为什么费这么大劲非要用printf输出,而不是直接用Python自带的print?

python的print和c的printf有什么区别

print([object, ...], *, sep=' ', end='\n', file=sys.stdout, flush=False)

输出对象到流文件,sep指定分割符,end指定结束符。参数转换为字符串写入输出流,如果没有输出内容直接输出end结束符。file参数必须是包含write方法的对象,默认输出到标准输出。

int printf( char * format, ... );

根据参数 format 字符串来转换并格式化数据,然后将结果输出到标准输出设备(显示器),直到出现字符串结束('\0')为止。
参数 format 字符串可包含下列三种字符类型:

一般文本,将会直接输出
ASCII 控制字符,如\t、\n 等有特定含义
格式转换字符

格式转换为一个百分比符号(%)及其后的格式字符所组成。一般而言,每个%符号在其后都必需有一个参数与之相呼应(只有当%%转换字符出现时会直接输出%字符),而欲输出的数据类型必须与其相对应的转换字符类型相同。

Python 相关文章推荐
Python实现国外赌场热门游戏Craps(双骰子)
Mar 31 Python
详解C++编程中一元运算符的重载
Jan 19 Python
Python中Collections模块的Counter容器类使用教程
May 31 Python
Windows环境下python环境安装使用图文教程
Mar 13 Python
Python Requests模拟登录实现图书馆座位自动预约
Apr 27 Python
Python列表常见操作详解(获取,增加,删除,修改,排序等)
Feb 18 Python
Django自定义模板过滤器和标签的实现方法
Aug 21 Python
Python实现大数据收集至excel的思路详解
Jan 03 Python
Python连接HDFS实现文件上传下载及Pandas转换文本文件到CSV操作
Jun 06 Python
python名片管理系统开发
Jun 18 Python
用Python开发app后端有优势吗
Jun 29 Python
Visual Studio code 配置Python开发环境
Sep 11 Python
使用Python实现博客上进行自动翻页
Aug 23 #Python
Python模拟鼠标点击实现方法(将通过实例自动化模拟在360浏览器中自动搜索python)
Aug 23 #Python
Python PyQt5标准对话框用法示例
Aug 23 #Python
Python PyQt5实现的简易计算器功能示例
Aug 23 #Python
Python实现的密码强度检测器示例
Aug 23 #Python
python+selenium+autoit实现文件上传功能
Aug 23 #Python
Django与JS交互的示例代码
Aug 23 #Python
You might like
thinkphp中连接oracle时封装方法无法用的解决办法
2013/06/17 PHP
php实现约瑟夫问题的方法小结
2015/03/23 PHP
php微信公众平台交互与接口详解
2016/11/28 PHP
php 判断IP为有效IP地址的方法
2018/01/28 PHP
关于innerHTML后丢失动态绑定的EVENT问题解决方法
2013/05/19 Javascript
JavaScript异步编程Promise模式的6个特性
2014/04/03 Javascript
jQuery解析Json实例详解
2015/11/24 Javascript
百度地图给map添加右键菜单(判断是否为marker)
2016/03/04 Javascript
js仿支付宝填写支付密码效果实现多方框输入密码
2016/03/09 Javascript
js添加事件的通用方法推荐
2016/05/15 Javascript
jquery请求servlet实现ajax异步请求的示例
2017/06/03 jQuery
Vue.js表单标签中的单选按钮、复选按钮和下拉列表的取值问题
2017/11/22 Javascript
JavaScript实现元素滚动条到达一定位置循环追加内容
2017/12/28 Javascript
浅谈vue父子组件怎么传值
2018/07/21 Javascript
如何在JavaScript中优雅的提取循环内数据详解
2019/03/04 Javascript
微信小程序如何播放腾讯视频的实现
2019/09/20 Javascript
Vue3.0中的monorepo管理模式的实现
2019/10/14 Javascript
[47:50]Secret vs VP 2018国际邀请赛小组赛BO2 第二场 8.17
2018/08/20 DOTA
[59:00]OG vs TNC 2018国际邀请赛小组赛BO2 第一场 8.19
2018/08/21 DOTA
[01:03:33]Alliance vs TNC 2019国际邀请赛小组赛 BO2 第一场 8.16
2019/08/18 DOTA
python插入排序算法实例分析
2015/07/03 Python
[原创]pip和pygal的安装实例教程
2017/12/07 Python
Python 实现引用其他.py文件中的类和类的方法
2018/04/29 Python
python实现汽车管理系统
2018/11/30 Python
Python父目录、子目录的相互调用方法
2019/02/16 Python
一个可以套路别人的python小程序实例代码
2019/04/09 Python
如何基于Python实现电子邮件的发送
2019/12/16 Python
在django中查询获取数据,get, filter,all(),values()操作
2020/08/09 Python
html5中localStorage本地存储的简单使用
2017/06/16 HTML / CSS
Betsey Johnson官网:妖娆可爱的连衣裙及鞋子、手袋和配件
2016/12/30 全球购物
2014年护士工作总结范文
2014/11/11 职场文书
特此通知格式
2015/04/27 职场文书
《珍珠鸟》教学反思
2016/02/16 职场文书
学校2016年九九重阳节活动总结
2016/04/01 职场文书
公司年会晚会开幕词
2019/04/02 职场文书
Windows server 2012 配置Telnet以及用法详解
2022/04/28 Servers