自己在使用Python实现周期执行的任务时,通常会用time.sleep()函数实现,但该方法能实现的最小周期只有30ms左右,且定时不够精确,大概有±5ms左右的跳动。该方法可满足绝大多数应用场景,但对某些实时性要求较高的应用场景则不适用。
查阅资料得知,在Winmm.dll中提供的多媒体定时器可实现精度1ms的高精度定时,而且使用方法也颇为简单,只需要通过ctypes模块导入动态链接库并访问动态链接库中的函数即可。
以创建周期5ms,定时精度为1ms的多媒体定时器为例,部分代码如下:
from ctypes import *
# 导入动态链接库
self._winmm = windll.LoadLibrary('winmm.dll')
# 定义传入多媒体定时器的回调函数
self._cb = CFUNCTYPE(c_void_p, c_void_p, c_void_p, c_void_p, c_void_p, c_void_p)(self._timer_callback)
# 使用timeSetEvent创建定时器
self._timerId = self._winmm.timeSetEvent(5, 1, self._cb, 0, 1)
# 在此添加需要在多媒体定时器中执行的程序
def _timer_callback(self, uID, uMsg, dwUser, dw1, dw2):
print(time.time())
程序结束时应销毁多媒体定时器,部分代码如下:
self._winmm.timeKillEvent(self._timerId)