Python设置定时任务

如果需要用Python实现定时任务,包括多长时间之后执行、每隔多久循环执行、每天的几点执行等,都算定时任务。实现定时任务的方法很多,python自身的库也有多种方式可以实现。其中最简单好用的一个库我感觉是threading库中的Timer。

比如每隔5秒执行一次:

import threading

def do_job():
    print('Just do it!')
    global timer
    timer = threading.Timer(5, do_job)
    timer.start()

timer = threading.Timer(1, do_job)
timer.start()

上面的代码中要循环执行的任务就是do_job函数,利用threading.Timer就可以循环执行,其中第一个参数是等待的时间,单位为秒s,可以是浮点数。第二个参数是要执行的函数。为了实现循环执行,只需要在每次执行任务时继续递归调用就可以了,但是timer记得设为global,节省内存。

但是如果要设置每天定时执行,那可能算时间算起来就比较麻烦,为了使用方便这里也提供一个简单的写好的函数:

import threading

def do_job():
    print('Just do it!')
    global timer
    timer = threading.Timer(86400, do_job) # 86400秒就是一天
    timer.start()

# 计算当前时间到明日某时间的秒数差
def get_interval_secs():
    tomorrow = (datetime.date.today() + datetime.timedelta(days=1)).strftime('%Y%m%d')
    tomorrow_time = tomorrow + "-09:00:00"
    tomorrow_time_date = datetime.datetime.strptime(tomorrow_time, '%Y%m%d-%H:%M:%S')
    now = datetime.datetime.now()
    interval = tomorrow_time_date - now
    secs = interval.total_seconds()
    return secs

# 测试计算到今日某时的时间差
def get_interval_secs_test():
    today = (datetime.date.today()).strftime('%Y%m%d')
    today_time = today + "-16:16:00"
    today_time_date = datetime.datetime.strptime(today_time, '%Y%m%d-%H:%M:%S')
    now = datetime.datetime.now()
    print(now)
    interval = today_time_date - now
    secs = interval.total_seconds()
    return secs

timer = threading.Timer(get_interval_secs(), do_report)
timer.start()

上面的代码中,首先把任务中的调用改成定时 成一天后再执行。然后在第一次调用时,我们利用get_interval_secs函数来计算当前时间点到明日某个要求的时间点的秒数差,作为第一次Timer的参数。在自己测试的过程中,可以使用第二个get_interval_secs_test函数来计算当前时间点到今日某个时间点的描述差来执行。

进一步优化可以改为一个函数:

import threading

def do_job():
    print('Just do it!')
    global timer
    timer = threading.Timer(86400, do_job) # 86400秒就是一天
    timer.start()

# 计算当前时间到指定时间点的描述差
def get_interval_secs(target_time):
    today = (datetime.date.today()).strftime('%Y%m%d')
    today_time = today + "-" + target_time
    today_time_date = datetime.datetime.strptime(today_time, '%Y%m%d-%H:%M:%S')
    now = datetime.datetime.now()
    interval = today_time_date - now
    secs = interval.total_seconds()
    if (secs > 0): return secs
    else: return secs + 86400

timer = threading.Timer(get_interval_secs("21:00:00"), do_report)
timer.start()

这个函数直接判断目标时间点是否还能在今天执行(与目前时间点算差值看是正是负),如果能今天执行(时间点还未到来),则到时候执行,如果来不及了,那就明天那时候再执行。


另外也可以用一个很方便且轻量的第三方库:schedule

按照其github(https://github.com/dbader/schedule)中的例子,使用起来很简单:

import schedule
import time

def job():
    print("I'm working...")

schedule.every(10).seconds.do(job) # 每10秒执行一次
schedule.every(10).minutes.do(job) # 每10分钟执行一次
schedule.every().hour.do(job) # 每小时执行一次
schedule.every().day.at("10:30").do(job) # 每天十点半执行
schedule.every(5).to(10).minutes.do(job) # 不理解
schedule.every().monday.do(job) # 每周一执行
schedule.every().wednesday.at("13:15").do(job) # 每周三13点15执行
schedule.every().minute.at(":17").do(job) # 不理解

while True:
    schedule.run_pending() # 运行所有可运行的任务
    time.sleep(1)

如果要执行带参数的任务,那只需要在函数名后跟参数即可,比如:

import schedule
import time

def job(job_name):
    print("I'm working on " + job_name)

schedule.every(10).seconds.do(job, job_name) # 每10秒执行一次
schedule.every(10).minutes.do(job, job_name) # 每10分钟执行一次

while True:
    schedule.run_pending() # 运行所有可运行的任务
    time.sleep(1)

这个库用起来实在太简单,以致于宁愿多折腾一点,比如如果你要在特殊环境里开发,不想每次都要安装这个库(比如在容器中),那也可以直接把这个库的代码包放到你的代码目录下,也就是github项目中的schedule文件夹,只需要这个就可以正常import调用了,无须安装。


查看作者首页

参考文章:
https://lz5z.com/Python%E5%AE%9A%E6%97%B6%E4%BB%BB%E5%8A%A1%E7%9A%84%E5%AE%9E%E7%8E%B0%E6%96%B9%E5%BC%8F/
https://blog.csdn.net/saltriver/article/details/52194915
https://blog.csdn.net/liao392781/article/details/80521194

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 217,907评论 6 506
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 92,987评论 3 395
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 164,298评论 0 354
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,586评论 1 293
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,633评论 6 392
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,488评论 1 302
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,275评论 3 418
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 39,176评论 0 276
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,619评论 1 314
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,819评论 3 336
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,932评论 1 348
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,655评论 5 346
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,265评论 3 329
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,871评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,994评论 1 269
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 48,095评论 3 370
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,884评论 2 354

推荐阅读更多精彩内容

  • 领教英国人民对园艺的热情,只需要去一趟垃圾厂。 花草树木的残骸被单独分类为花园垃圾,不能同生活垃圾或者可回收垃圾混...
    树皮蚯蚓阅读 1,003评论 0 1
  • 想往深圳考。 一年能等吗? 太难了吧?!
    这样就认不出来惹阅读 157评论 0 0