python单线程实现多个定时器示例


Posted in Python onMarch 30, 2014

单线程实现多个定时器

NewTimer.py

#!/usr/bin/env python
from heapq import *
from threading import Timer
import threading
import uuid
import time
import datetime
import sys
import math
global TimerStamp
global TimerTimes
class CancelFail(Exception):
    pass
class Slot(object):
    def __init__(self, period=0, interval=1, function=None, args=[], kwargs={}):
        self.period = period
        self.pc = 0
        self.interval = interval
        self.fire = 0
        self.id = uuid.uuid1()
        self.function = function
        self.args = args
        self.kwargs = kwargs
#system resolution millisecond         
class NewTimer(object):
    #set enough time make thread sleep, when NewTimer empty set enoug time, too
    #make sure sum of your timer call back function execute time shorter than resolution
    #todo use a worker thread to operate timer call back function
    def __init__(self, resolution=1000):
        global TimerStamp
        TimerStamp = int(time.time() * 1000)
        self.nofire = sys.maxint #next fire time interval
        self.firestamp = self.nofire + TimerStamp
        self.resolution = resolution# 1s
        self.lock = threading.RLock()
        self.wait = dict()
        self.ready = dict()
        self._start()
    """ private operate ready list """
    def _addToReadyList(self, slot, firestamp):
        box = dict( [ (slot.id, slot)])
        if not self.ready.has_key( firestamp ):
            self.ready.update( [(firestamp, box)] )
        else:
            boxs = self.ready.get(firestamp)
            boxs.update( box )
    def _delFromReadyList(self, slot):
        boxs = self.ready.get(slot.fire)
        try:
            box = boxs.pop(slot.id)
            if not boxs:
                self.ready.pop(slot.fire)
        except (AttributeError, KeyError):
            raise CancelFail
    """ inside """
    def _start(self):
        global TimerStamp
        try:
            self.firestamp = sorted( self.ready.keys() )[0]
            stamp = float((TimerStamp + self.firestamp - int(time.time()*1000)))/1000
        except IndexError:
            self.firestamp = self.nofire
            stamp = self.nofire
        try:
            self.timer.cancel()
        except AttributeError:
            pass
        self.timer = Timer( stamp, self.hander)
        self.timer.start()
    def hander(self, *args, **kwargs):
        """ find time arrive slot, do it function """
        self.lock.acquire()
        try:
            boxs = self.ready.pop( self.firestamp )
            slots = boxs.values()
        except KeyError:
            slots = []
        for slot in slots:
            if slot.period:
                slot.pc += 1
                if slot.pc != slot.period:
                    slot.fire = slot.interval + slot.fire
                    self._addToReadyList(slot, slot.fire)
            elif slot.period == -1:
                slot.fire = slot.interval + slot.fire
                self._addToReadyList(slot, slot.fire)
        """ """
        self._start()
        self.lock.release()
        for slot in slots:
            try:
                slot.function(slot.args, slot.kwargs)
            except Exception:
                print "slot id %s, timer function fail" % slot.id
    """ operate new timer manager itself """
    def stop(self):
        self.timer.cancel()
    """ new timer manager """
    def add(self, period=0, interval=1, function=None, args=[], kwargs={}):
        """
        period: one time = 0, times = >0, always = -1
        interval: timer fire relative TimerReference
        function: when timer fire, call back function
        args,kwargs: callback function args
        """ 
        interval = int(interval) * self.resolution#seconds
        if interval < self.resolution:
            interval = self.resolution
        slot = Slot( period, interval, function, *args, **kwargs )
        box = dict([(slot.id, slot)])
        self.wait.update(box)
        return slot
    def remove(self, slot):
        if isinstance(slot, Slot):
            self.cancel(slot)
            try:
                self.wait.pop(slot.id)
            except KeyError:
                print "wait dict not has the cancel timer"
    """ timer api """
    def reset(self, slot):
        if isinstance(slot, Slot):
            self.cancel(slot)
            slot.pc = 0
            self.start(slot)
    def start(self, slot):
        def NewTimerStamp(timebase, resolution):
            nowoffset = int(time.time() * 1000) - timebase
            if nowoffset % resolution < resolution / 10:
                currentstamp =  nowoffset / resolution
            else:
                currentstamp = (nowoffset + resolution - 1) / resolution
            return currentstamp * 1000
        global TimerStamp
        if isinstance(slot, Slot):
            firestamp = slot.interval + NewTimerStamp(TimerStamp, self.resolution)
            slot.fire = firestamp
            self.lock.acquire()
            self._addToReadyList(slot, firestamp)
            if self.firestamp > slot.fire:
                self._start()
            self.lock.release()
    def cancel(self, slot):
        if isinstance(slot, Slot):
            try:  
                self.lock.acquire()
                self._delFromReadyList(slot)
                self._start()
                self.lock.release()
            except CancelFail:
                self.lock.release()
def hello( *args, **kargs):
    print args[0], datetime.datetime.now()
if __name__ == "__main__":
    print "start test timer", datetime.datetime.now()
    nt = NewTimer(500)
    t0 = nt.add( -1, 5, hello, [0])
    t1 = nt.add( 4, 7, hello, [1])
    t2 = nt.add( 1, 3, hello, [2])#
    t3 = nt.add( 1, 4, hello, [3])#
    t4 = nt.add( 4, 5, hello, [4])
    t5 = nt.add( 12, 5, hello, [5])#
    t6 = nt.add( 9, 7, hello, [6])
    t7 = nt.add( 1, 8, hello, [7])#
    t8 = nt.add( 40, 1, hello, [8])
    nt.start( t0 )
    nt.start( t1 )
    nt.start( t2 )#
    nt.start( t3 )#
    nt.start( t4 )
    nt.start( t5 )#
    nt.start( t6 )
    nt.start( t7 )#
    nt.start( t8 )
    nt.cancel(t2)
    nt.cancel(t3)
    nt.remove(t5)
    nt.remove(t3)
    time.sleep(3)
    nt.start(t2)
    nt.cancel(t8)
    time.sleep(300)
    nt.stop()
    print "finish test timer", datetime.datetime.now()
Python 相关文章推荐
详解在Python程序中自定义异常的方法
Oct 16 Python
python实现简单聊天应用 python群聊和点对点均实现
Sep 14 Python
Python爬虫实例_利用百度地图API批量获取城市所有的POI点
Jan 10 Python
Tensorflow 实现修改张量特定元素的值方法
Jul 30 Python
10 行 Python 代码教你自动发送短信(不想回复工作邮件妙招)
Oct 11 Python
pytorch 固定部分参数训练的方法
Aug 17 Python
python django中8000端口被占用的解决
Dec 17 Python
基于Pycharm加载多个项目过程图解
Jan 19 Python
Python 面向对象之类class和对象基本用法示例
Feb 02 Python
Android Q之气泡弹窗的实现示例
Jun 23 Python
详解Python中的路径问题
Sep 02 Python
python类共享变量操作
Sep 03 Python
python实现猜数字游戏(无重复数字)示例分享
Mar 29 #Python
使用python实现扫描端口示例
Mar 29 #Python
Python Trie树实现字典排序
Mar 28 #Python
python实现探测socket和web服务示例
Mar 28 #Python
python实现目录树生成示例
Mar 28 #Python
python改变日志(logging)存放位置的示例
Mar 27 #Python
使用python删除nginx缓存文件示例(python文件操作)
Mar 26 #Python
You might like
php 从数据库提取二进制图片的处理代码
2009/09/09 PHP
linux下删除7天前日志的代码(php+shell)
2011/01/02 PHP
最常用的8款PHP调试工具
2014/07/06 PHP
phpmyadmin中禁止外网使用的方法
2014/11/04 PHP
php从数据库中获取数据用ajax传送到前台的方法
2018/08/20 PHP
thinkPHP框架通过Redis实现增删改查操作的方法详解
2019/05/13 PHP
Yii2框架控制器、路由、Url生成操作示例
2019/05/27 PHP
JavaScript语句可以不以;结尾的烦恼
2007/03/08 Javascript
JQuery 选项卡效果(JS与HTML的分离)
2010/04/01 Javascript
js多级树形弹出一个小窗口层(非常好用)实例代码
2013/03/19 Javascript
将input file的选择的文件清空的两种解决方案
2013/10/21 Javascript
jquery实现倒计时代码分享
2014/06/13 Javascript
JavaScript事件委托技术实例分析
2015/02/06 Javascript
JS实现跟随鼠标闪烁转动色块的方法
2015/02/26 Javascript
JavaScript黑洞数字之运算路线查找算法(递归算法)实例
2016/01/28 Javascript
JS实现可编辑的后台管理菜单功能【附demo源码下载】
2016/09/13 Javascript
js 打开新页面在屏幕中间的实现方法
2016/11/02 Javascript
Python中AND、OR的一个使用小技巧
2015/02/18 Python
Python元组常见操作示例
2019/02/19 Python
如何在mac环境中用python处理protobuf
2019/12/25 Python
python 牛顿法实现逻辑回归(Logistic Regression)
2020/10/15 Python
python+requests实现接口测试的完整步骤
2020/10/27 Python
Python系统公网私网流量监控实现流程
2020/11/23 Python
Jacques Lemans德国:奥地利钟表品牌
2019/12/26 全球购物
广告学专业自荐信范文
2014/02/24 职场文书
保密普查工作实施方案
2014/02/25 职场文书
小学生评语大全
2014/04/18 职场文书
文明礼貌演讲稿
2014/05/12 职场文书
ktv周年庆活动方案
2014/08/18 职场文书
大学本科生职业生涯规划书范文
2014/09/14 职场文书
民主生活会对照检查材料(统计局)
2014/09/21 职场文书
2014年党员教师自我剖析材料
2014/09/30 职场文书
2016年寒假社会实践活动总结
2015/03/27 职场文书
盗窃案辩护词
2015/05/21 职场文书
小人国观后感
2015/06/11 职场文书
Python使用永中文档转换服务
2022/05/06 Python