在
enum
模块出现之前,c_int
或相关类型经常被用作替代枚举。但这没有类型检查。
现在Python有了一个enum
模块,是否有一种方法可以直接与ctypes
一起使用呢?
是的,我们可以通过ctypes轻松创建自己的CEnum类,这得益于ctypes允许我们使用自定义类的选项。枚举类型由ctypes自动检查。
from ctypes import windll
from enum import IntEnum
class CEnum(IntEnum):
@classmethod
def from_param(cls, self):
if not isinstance(self, cls):
raise TypeError
return self
class EnumA(CEnum):
CONST = 0
class EnumB(CEnum):
CONST = 0
以下是一个示例(虽然滥用类型,但正确展示了用法):
windll.kernel32.GetModuleHandleA.argtypes = [EnumA]
>>> windll.kernel32.GetModuleHandleA(EnumA.CONST)
>>> windll.kernel32.GetModuleHandleA(EnumB.CONST)
ArgumentError: argument 1: <class 'TypeError'>:
顺便提一下,我已经转换到CFFI,它原生支持枚举类型,并且使用的是 C 定义,这比 ctype 更加简洁。
ctypes.Structure
定义中将CEnum
子类用作C类型。我已经为此提出了一个新的问题(http://stackoverflow.com/questions/36877391/using-an-intenum-as-the-type-in-a-ctypes-structure-fields)。 - Vlad Firoiu