回过头来,再看一下windll和oledll的差别,这两者之间最大的差别是oledll调用的函数都是固定返回HRESULT类型的值,而windll是不固定的类型的。在Python 3.3版本号之前,都是返回命名为OSError类型错误,在这之后就返回命名为WindowsError类型错误。

通一大段的讨论,我们彻底地了解cdll、windll和oledll之间的差别。为了更加清晰地记住它们,总结例如以下表所看到的:

表2-1:

对象名称

參数入栈顺序

清栈方式

返回值类型

cdll

从右向左

调用者

不固定

windll

从右向左

被调用者

不固定

oledll

从右向左

被调用者

WindowsError

windll对象

调用WIN32的API函数,主要是通过windll对象来实现。那windll是何许人也?因为Python是开源的项目,我们非常方便就定位到它的源代码库里,查看它的实现方式。这样对于了解windll背后的秘密带来了极大的方便,假设是商业的项目就比較艰难了。

在Milang或者Python的安装文件夹下,例如以下:

E:\Milang\python\Lib\ctypes

就能够找到ctypes库,这个库是通过包来公布的,因此在此文件夹下看到__init__.py文件。这个文件就是ctypes库导入时最初执行的文件,那么cdll、windll和oledll对象就是在这里创建的。与这里讨论相关的代码例如以下:

...

cdll = LibraryLoader(CDLL)

pydll = LibraryLoader(PyDLL)

if _os.name in ("nt", "ce"):

pythonapi = PyDLL("python dll", None, _sys.dllhandle)

elif _sys.platform == "cygwin":

pythonapi = PyDLL("libpython%d.%d.dll" % _sys.version_info[:2])

else:

pythonapi = PyDLL(None)

if _os.name in ("nt", "ce"):

windll = LibraryLoader(WinDLL)

oledll = LibraryLoader(OleDLL)

...

通过这段代码能够看到,windll是LibraryLoader类的实例,它是一个WinDLL类型的对象。LibraryLoader的主要功能就是实现动态库连接库的搜索、载入和重载运算符。让在Python里使用动态连接库更加方便。到这里就能够来看这句代码的详细意思了:

MessageBox = windll.user32.MessageBoxW

windll就是前面创建的动态连接库载入对象,user32是Windows提供的WIN32的API接口的动态连接库的名称(user32.dll)。MessageBoxW是WIN32提供的弹出一个提示框的函数名称。在这行代码里。有意思的是并没有採用传送參数的方式来訪问不同的动态连接库。而通过属性的方式(点号执行)来选择不同的动态连接库。

在这里.user32就是表示訪问动态连接user32.dll。像以下这行代码:

windll.kernel32.GetModuleHandleW(None)

就是表示訪问动态连接库kernel32.dll,因此訪问动态连接库gdi32.dll,就是变成这样:

windll.gdi32

通过点号运算就能够方便地载入不同的动态连接库。这是因为LibraryLoader类在后面进行点号运算符进行重载的结果。这样使用起来更方便和更清晰,比传送參数打更少的代码。在Windows里主要提供以下三个动态连接来对Windows的功能调用。例如以下:

kernel32.dll是Windows9x/Me中非常重要的32位动态链接库文件,属于内核级文件。它控制着系统的内存管理、数据的输入输出操作和中断处理,当Windows启动时,kernel32.dll就驻留在内存中特定的写保护区域,使别的程序无法占用这个内存区域。

user32.dll是Windows用户界面相关应用程序接口,用于包括Windows处理,基本用户界面等特性,如创建窗体和发送消息。

gdi32.dll是Windows GDI图形用户界面相关程序,包括的函数用来绘制图像和显示文字。

在这里有一点,你或许注意到了。当想调用MessageBox函数时,事实上是写的名称是MessageBoxW。在后面多了一个W。这个W是什么用的呢?事实上在WIN32的API里,提供了两套的API接口,一套是支持是UNICODE的API接口,一套是支持ANSI的API接口。说白了就是为了解决双字节和单字节的文字的显示问题。

因此,要想使用ANSI单字的API接口,要使用MessageBoxA的名称。

在我们编写C和C++程序时。仅仅须要使用MessageBox就能够了。事实上这是因为API在接口的头文件进行宏定义。在Python里没有必要进行这样的魔幻的操作,让人更加明了,明确。

windll对象的更多相关文章

  1. from声明

    在整个应用程序,只有三行声明.这是最短单WIN32应用,但它的功能是非常有限,简单地显示一个消息框,示出来,其他什么事情也没有做.以下就来分析这三行语句了.别小看这三行语句.其实是隐藏着非常多知识点在 ...

  2. cdll和windll的差别

    Python要想调用C语言写的动态连接库.不仅要兼容C接口的调用习惯,还须要兼容C语言的数据类型.幸运的是ctypes库已经做了这双方面的工作.以便调用动态连接库是很方便的.在Hello World的 ...

  3. 如何一步一步用DDD设计一个电商网站(九)—— 小心陷入值对象持久化的坑

    阅读目录 前言 场景1的思考 场景2的思考 避坑方式 实践 结语 一.前言 在上一篇中(如何一步一步用DDD设计一个电商网站(八)—— 会员价的集成),有一行注释的代码: public interfa ...

  4. javascript中的Array对象 —— 数组的合并、转换、迭代、排序、堆栈

    Array 是javascript中经常用到的数据类型.javascript 的数组其他语言中数组的最大的区别是其每个数组项都可以保存任何类型的数据.本文主要讨论javascript中数组的声明.转换 ...

  5. 探究javascript对象和数组的异同,及函数变量缓存技巧

    javascript中最经典也最受非议的一句话就是:javascript中一切皆是对象.这篇重点要提到的,就是任何jser都不陌生的Object和Array. 有段时间曾经很诧异,到底两种数据类型用来 ...

  6. Asp.Net WebApi核心对象解析(下篇)

    在接着写Asp.Net WebApi核心对象解析(下篇)之前,还是一如既往的扯扯淡,元旦刚过,整个人还是处于晕的状态,一大早就来处理系统BUG,简直是坑爹(好在没让我元旦赶过来该BUG),队友挖的坑, ...

  7. JS核心系列:浅谈原型对象和原型链

    在Javascript中,万物皆对象,但对象也有区别,大致可以分为两类,即:普通对象(Object)和函数对象(Function). 一般而言,通过new Function产生的对象是函数对象,其他对 ...

  8. Chrome出了个小bug:论如何在Chrome下劫持原生只读对象

    Chrome出了个小bug:论如何在Chrome下劫持原生只读对象 概述 众所周知,虽然JavaScript是个很灵活的语言,浏览器里很多原生的方法都可以随意覆盖或者重写,比如alert.但是为了保证 ...

  9. XStream将java对象转换为xml时,对象字段中的下划线“_”,转换后变成了两个的解决办法

            在前几天的一个项目中,由于数据库字段的命名原因 其中有两项:一项叫做"市场价格"一项叫做"商店价格" 为了便于区分,遂分别将其命名为market ...

随机推荐

  1. 类名引用static变量好处

    不仅强调了变量static的结构,而且在有些情况下他还为编译器进行优化提供了更好的机会.

  2. 1.18 Python基础知识 - Python内置函数

    官方地址:https://docs.python.org/3.5/library/functions.html abs(x): 返回数字的绝对值 all(iterable): 如果迭代器的所有元素都为 ...

  3. 关于编译com工程的一些体会

    作者:朱金灿 来源:http://blog.csdn.net/clever101 今天发现com的编译的一个重要一步是微软提供的midl工具将其中的idl文件生成一个头文件.c文件(即IID文件)和代 ...

  4. 转一篇对EJB理解的文章

    1. 我们不禁要问,什么是"服务集群"?什么是"企业级开发"? 既然说了EJB 是为了"服务集群"和"企业级开发",那么 ...

  5. Android圆环控件

    Android圆环控件 近期在做一个功能.界面效果要求例如以下: 看到这个界面,我首先想到了曾经在做phone模块的时候,我们定制的来电界面InCallTouchUi,界面效果是相似的. 来电控件使用 ...

  6. php课程 11-37 类和对象的关系是什么

    php课程 11-37 类和对象的关系是什么 一.总结 一句话总结:类生成对象,对象是类的实例化,一定是先有类,后有对象,一定是先有标准,再有个体. 1.oop的三大优势是什么? 重用性,灵活性.扩展 ...

  7. 16.用Spring Boot颠覆Java应用开发

    转自:https://www.cnblogs.com/aishangJava/p/5971288.html Java开发概述: 使用Java做Web应用开发已经有近20年的历史了,从最初的Servle ...

  8. [转]MySQLHelper类

    本文转自:http://de.cel.blog.163.com/blog/static/5145123620110181003903/ 类似于SQLHelper,只是这里引用的是MySql.Data类 ...

  9. iOS_01_C语言简介

    1.先学C语言的原因 * oc基于C. * oc 跟 C的思想和语法很多地方不太一样,而且OC能和C混用. * C 是所有编程语言中的经典,很多高级语言都是从C语言中衍生出来的,比如 C++,C#.O ...

  10. numpy 高阶函数 —— np.histogram

    np.diff(a, n=1, axis=-1):n 表示差分的阶数: >> x = np.array([1, 2, 4, 7, 0]) >> np.diff(x) array ...