1、Timer 类

构造器

 //默认定时器名称public Timer() {this("Timer-" + serialNumber());}//以守护进程的方式运行此定时器public Timer(boolean isDaemon) {this("Timer-" + serialNumber(), isDaemon);}//自定义定时器名称public Timer(String name) {thread.setName(name);thread.start();}public Timer(String name, boolean isDaemon) {thread.setName(name);thread.setDaemon(isDaemon);thread.start();}

schedule

 //计划在指定的延迟后执行指定的任务,以毫秒为单位public void schedule(TimerTask task, long delay) {if (delay < 0)throw new IllegalArgumentException("Negative delay.");sched(task, System.currentTimeMillis()+delay, 0);}//计划在指定时间执行指定任务。如果时间已过,则计划立即执行任务// long delay 跟 Date time 的区别:delay 必须大于0,即未来时间;time可以是过去时间public void schedule(TimerTask task, Date time) {sched(task, time.getTime(), 0);}//将指定的任务安排为重复的固定延迟执行,从指定的延迟之后开始。//随后大约每隔一定的时间间隔重复执行。都是以毫秒为单位public void schedule(TimerTask task, long delay, long period) {if (delay < 0)throw new IllegalArgumentException("Negative delay.");if (period <= 0)throw new IllegalArgumentException("Non-positive period.");sched(task, System.currentTimeMillis()+delay, -period);}public void schedule(TimerTask task, Date firstTime, long period) {if (period <= 0)throw new IllegalArgumentException("Non-positive period.");sched(task, firstTime.getTime(), -period);}//以毫秒为单位,在指定的时间和指定的时间段安排指定的计时器任务执行。//如果周期为正,则计划重复执行任务;如果周期为零,则计划一次性执行任务private void sched(TimerTask task, long time, long period) {if (time < 0)throw new IllegalArgumentException("Illegal execution time.");// Constrain value of period sufficiently to prevent numeric// overflow while still being effectively infinitely large.if (Math.abs(period) > (Long.MAX_VALUE >> 1))period >>= 1;synchronized(queue) {if (!thread.newTasksMayBeScheduled)throw new IllegalStateException("Timer already cancelled.");synchronized(task.lock) {if (task.state != TimerTask.VIRGIN)throw new IllegalStateException("Task already scheduled or cancelled");task.nextExecutionTime = time;task.period = period;task.state = TimerTask.SCHEDULED;}queue.add(task);if (queue.getMin() == task)queue.notify();}}
    public static void main(String[] args) throws InterruptedException {demo01();}public static void demo01() throws InterruptedException {Timer timer = new Timer();log.info("=============第一次启动定时器=============");timer.schedule(new TimerTask() {@Overridepublic void run() {log.info("一次性执行,启动定时器延迟3秒执行");}}, 3000);Thread.sleep(5000);log.info("=============第二次启动定时器=============");timer.schedule(new TimerTask() {@Overridepublic void run() {try {Thread.sleep(3000);log.info("周期性执行,启动定时器延迟3秒执行,之后每隔2秒执行一次,但如果任务时间超过2秒则以任务时间为间隔");} catch (InterruptedException e) {e.printStackTrace();}}}, 3000, 2000);}

scheduleAtFixedRate

 //将指定的任务安排为重复的固定速率执行,从指定的延迟后开始。//随后大约每隔一定的时间间隔进行,并按规定的时间间隔进行。public void scheduleAtFixedRate(TimerTask task, long delay, long period) {if (delay < 0)throw new IllegalArgumentException("Negative delay.");if (period <= 0)throw new IllegalArgumentException("Non-positive period.");sched(task, System.currentTimeMillis()+delay, period);}public void scheduleAtFixedRate(TimerTask task, Date firstTime,long period) {if (period <= 0)throw new IllegalArgumentException("Non-positive period.");sched(task, firstTime.getTime(), period);}
    public static void demo02() {Timer timer = new Timer();log.info("=============开始启动定时器=============");timer.scheduleAtFixedRate(new TimerTask() {@Overridepublic void run() {try {Thread.sleep(3000);log.info("周期性执行,启动定时器延迟3秒执行,之后每隔2秒执行一次,但如果任务时间超过2秒则以任务时间为间隔");} catch (InterruptedException e) {e.printStackTrace();}}}, 3000, 2000);}

2、ScheduledThreadPoolExecutor

    @Bean(name = "scheduledPoolTaskExecutor", destroyMethod = "shutdown")public ScheduledThreadPoolExecutor scheduledThreadPoolExecutor() {// 第一个参数:核心线程数// 第二个参数:线程工厂(此处用来设置线程名)// 第三次参数:饱和策略// 饱和策略// AbortPolicy:直接抛出java.util.concurrent.RejectedExecutionException异常// CallerRunsPolicy:若已达到待处理队列长度,将由主线程直接处理请求// DiscardOldestPolicy:抛弃旧的任务;会导致被丢弃的任务无法再次被执行// DiscardPolicy:抛弃当前任务;会导致被丢弃的任务无法再次被执行return new ScheduledThreadPoolExecutor(10,new ThreadFactory() {int i = 0;@Overridepublic Thread newThread(Runnable r) {return new Thread(r, "scheduled-" + i++);}},new ThreadPoolExecutor.DiscardPolicy());}@Slf4j
@Component
public class PoolTaskDemo {@Resource(name = "scheduledPoolTaskExecutor")private ScheduledThreadPoolExecutor scheduled;@PostConstructpublic void scheduledPoolTaskExecutor() {schedule();
//        scheduleAtFixedRate();
//        scheduleWithFixedDelay();}public void schedule() {log.info("调用前");scheduled.schedule(new Runnable() {@Overridepublic void run() {log.info("方法调用,延迟5秒执行一次, 只执行一次");}}, 5000, TimeUnit.MILLISECONDS);}
}

    public void scheduleAtFixedRate() {log.info("调用前");scheduled.scheduleAtFixedRate(new Runnable() {@SneakyThrows@Overridepublic void run() {log.info("方法调用,延迟5秒首次执行,之后每过3秒轮询, 不受run方法执行耗时影响");Thread.sleep(2000);}}, 5000, 3000, TimeUnit.MILLISECONDS);}

    public void scheduleWithFixedDelay() {log.info("调用前");scheduled.scheduleWithFixedDelay(new Runnable() {@SneakyThrows@Overridepublic void run() {log.info("方法调用,延迟5秒首次执行,之后每过3秒轮询,受run方法执行耗时影响");Thread.sleep(2000);}}, 5000, 3000, TimeUnit.MILLISECONDS);}

3、@Scheduled

@Configuration
@EnableScheduling // 使@Scheduled生效
public class ScheduledConfig implements SchedulingConfigurer {@Overridepublic void configureTasks(ScheduledTaskRegistrar scheduledTaskRegistrar) {scheduledTaskRegistrar.setScheduler(scheduledThreadPoolExecutor());}@Bean(name = "scheduledPoolTaskExecutor", destroyMethod = "shutdown")public ScheduledThreadPoolExecutor scheduledThreadPoolExecutor() {// 第一个参数:核心线程数// 第二个参数:线程工厂(此处用来设置线程名)// 第三次参数:饱和策略// 饱和策略// AbortPolicy:直接抛出java.util.concurrent.RejectedExecutionException异常// CallerRunsPolicy:若已达到待处理队列长度,将由主线程直接处理请求// DiscardOldestPolicy:抛弃旧的任务;会导致被丢弃的任务无法再次被执行// DiscardPolicy:抛弃当前任务;会导致被丢弃的任务无法再次被执行return new ScheduledThreadPoolExecutor(10,new ThreadFactory() {int i = 0;@Overridepublic Thread newThread(Runnable r) {return new Thread(r, "scheduled-" + i++);}},new ThreadPoolExecutor.DiscardPolicy());}}

fixedRate

@Slf4j
@Component
public class ScheduledDemo {@Scheduled(fixedRate = 5000)public void fixedRate() throws InterruptedException {log.info("项目启动时立即执行第一次,之后每过5秒固定执行一次,不受方法执行耗时影响");Thread.sleep(2000);}
}

fixedDelay

    @Scheduled(fixedDelay = 5000)public void fixedDelay() throws InterruptedException {log.info("项目启动时立即执行第一次,方法内部执行完成之后过5秒再次执行,受方法执行耗时影响");Thread.sleep(2000);}

initialDelay

    @Scheduled(initialDelay = 5000,fixedRate = 10000)public void initialDelayFixedRate() throws InterruptedException {log.info("项目启动时延迟5秒才执行第一次,在第一次执行后每过10秒固定执行一次,不受方法执行耗时影响");Thread.sleep(2000);}

cron

    @Scheduled(cron = "0/5 * * * * ? ")public void cron() throws InterruptedException {log.info("项目启动时延迟5秒才执行第一次,在第一次执行时每过5秒固定执行一次,不受方法执行耗时影响");Thread.sleep(2000);}

    @Scheduled(cron = "5 * * * * ? ")public void cron2() throws InterruptedException {log.info("每分钟的刚好第5秒时,执行一次,不受方法执行耗时影响");Thread.sleep(2000);}

cron表达式

cronExpression定义时间规则,Cron表达式由6或7个空格分隔的时间字段组成:秒 分钟 小时 日期 月份 星期 年(可选)字段  允许值    允许的特殊字符
秒       0-59     , - * /
分       0-59     , - * /
小时      0-23     , - * /
日期      1-31     , - * ? / L W C
月份      1-12     , - * /
星期      1-7      , - * ? / L C #
年     1970-2099     , - * /特殊符号 代表含义
,       枚举
-       区间
*       任意
/       步长
?       日/星期冲突匹配
L       最后
W       工作日
C       和Calendar联系后计算过的值
#       星期 4#2 第2个星期四如:
"*": 字符被用来指定所有的值。如:在分钟字段域里表示“每分钟”
"?":字符只在日期域和星期域中使用。它被用来指定“非明确的值”。
"-":字符被用来指定一个范围。如:“10-12”在小时域意味着“10点、11点、12点”。
",":字符被用来指定另外的值。如:“MON,WED,FRI”在星期域里表示”星期一、星期三、星期五”。
"/":字符用于指定增量。如:"0/5"在秒域0秒开始,每过5秒触发一次,"5/15"在分钟域表示每小时的5,20,35和50。
符号"*"在"/"前面(如:*/10)等价于0在“/”前面(如:0/10)。L是‘last’的省略写法可以表示day-of-month和day-of-week域,但在两个字段中的意思不同,例如day-of- month域中表示一个月的最后一天。
如果在day-of-week域表示‘7’或者‘SAT’,如果在day-of-week域中前面加上数字,它表示 一个月的最后几天,例如‘6L’就表示一个月的最后一个星期五。
字符“W”只允许日期域出现。这个字符用于指定日期的最近工作日。例如:如果你在日期域中写 “15W”,表示:这个月15号最近的工作日。
所以,如果15号是周六,则任务会在14号触发。如果15好是周日,则任务会在周一也就是16号触发。
如果 是在日期域填写“1W”即使1号是周六,那么任务也只会在下周一,也就是3号触发,“W”字符指定的最近工作日是不能够跨月份的。
字符“W”只能配合一个 单独的数值使用,不能够是一个数字段,如:1-15W是错误的。
“L”和“W”可以在日期域中联合使用,LW表示这个月最后一周的工作日。
字符“#”只允许在星期域中出现。这个字符用于指定本月的某某天。例如:“6#3”表示本月第三周的星期五(6表示星期五,3表示第三周)。
“2#1”表示本月第一周的星期一。“4#5”表示第五周的星期三。
字符“C”允许在日期域和星期域出现。这个字符依靠一个指定的“日历”。也就是说这个表达式的值依赖于相关的“日历”的计算结果,如果没有“日历” 关联,则等价于所有包含的“日历”。
如:日期域是“5C”表示关联“日历”中第一天,或者这个月开始的第一天的后5天。星期域是“1C”表示关联“日历” 中第一天,或者星期的第一天的后1天,也就是周日的后一天(周一)。经典例子:
"0 0 10,14,16 * * ?"    每天上午10点,下午2点,4点
"0 0/30 9-17 * * ?"     朝九晚五工作时间内每半小时
"0 0 12 ? * WED"        表示每个星期三中午12点
"0 0 12 * * ?"          每天中午12点触发
"0 15 10 ? * *"         每天上午10:15触发
"0 15 10 * * ?"         每天上午10:15触发
"0 15 10 * * ? *"       每天上午10:15触发
"0 15 10 * * ? 2005"    2005年的每天上午10:15触发
"0 * 14 * * ?"          在每天下午2点到下午2:59期间的每1分钟触发
"0 0/5 14 * * ?"        在每天下午2点到下午2:55期间的每5分钟触发
"0 0/5 14,18 * * ?"     在每天下午2点到2:55期间和下午6点到6:55期间的每5分钟触发
"0 0-5 14 * * ?"        在每天下午2点到下午2:05期间的每1分钟触发
"0 10,44 14 ? 3 WED"    每年三月的星期三的下午2:10和2:44触发
"0 15 10 ? * MON-FRI"   周一至周五的上午10:15触发
"0 15 10 15 * ?"        每月15日上午10:15触发
"0 15 10 L * ?"         每月最后一日的上午10:15触发
"0 15 10 ? * 6L"        每月的最后一个星期五上午10:15触发
"0 15 10 ? * 6#3"       每月的第三个星期五上午10:15触发"30 * * * * ?"          每半分钟触发任务
"30 10 * * * ?"         每小时的10分30秒触发任务
"30 10 1 * * ?"         每天1点10分30秒触发任务
"30 10 1 20 * ?"        每月20号1点10分30秒触发任务
"30 10 1 20 10 ? *"     每年10月20号1点10分30秒触发任务
"30 10 1 20 10 ? 2011"  2011年10月20号1点10分30秒触发任务
"30 10 1 ? 10 * 2011"   2011年10月每天1点10分30秒触发任务
"30 10 1 ? 10 SUN 2011" 2011年10月每周日1点10分30秒触发任务
"15,30,45 * * * * ?"    15秒,30秒,45秒时触发任务
"15-45 * * * * ?"       15到45秒内,每秒都触发任务
"15/5 * * * * ?"        每分钟的每15秒开始触发,每隔5秒触发一次
"15-30/5 * * * * ?"     每分钟的15秒到30秒之间开始触发,每隔5秒触发一次
"0 0/3 * * * ?"         每小时的第0分0秒开始,每三分钟触发一次
"0 15 10 ? * MON-FRI"   星期一到星期五的10点15分0秒触发任务
"0 15 10 L * ?"         每个月最后一天的10点15分0秒触发任务
"0 15 10 LW * ?"        每个月最后一个工作日的10点15分0秒触发任务
"0 15 10 ? * 5L"        每个月最后一个星期四的10点15分0秒触发任务
"0 15 10 ? * 5#3"       每个月第三周的星期四的10点15分0秒触发任务

SpringBoot之定时器相关推荐

  1. Springboot实现定时器quartz应用举例。

    上一篇中我们说明了Springboot实现定时器quartz中文文档说明, 在开写主要内容前,我们来说明其他方式. 两者都是针对较简单的情况下.其一是,SpringBoot自带定时注解.其二是,定时线 ...

  2. springboot使用定时器及发送邮件

    1.定时器配置 本人springboot版本为2.2.5,不用额外配置pom.xml及applicaiton.properties属性,直接全注解形式实现,下面用一个简单的实例演示一下: /**@Co ...

  3. SpringBoot实现定时器定时处理任务

    最近在项目中遇到了一个问题, 对于新建的活动, 活动设置了开始时间和结束时间, 也就是数据库中的一个状态码的改变而已. 但是,这里就有问题了, 如何去实现到时间更改活动状态呢? 1. 刚开始的时候,我 ...

  4. SpringBoot启用定时器任务(基于注解,简单易上手)

    文章目录 前言 一.定时任务是什么? 二.代码实现 1.相关代码注解 2.注解用法 总结 前言   几乎在所有的项目中,定时任务的使用都是不可或缺的,例如生活中网上购物的日常,如果用户收到了商品而没有 ...

  5. springboot cron定时器

    定时任务一个类 package com.example.main.cron;import org.springframework.context.annotation.Configuration; i ...

  6. SpringBoot多线程环境下,解决多个定时器冲突问题

    欢迎关注方志朋的博客,回复"666"获面试宝典 来源:blog.csdn.net/cssnnd/article/details/108328942 战术分析: 实际开发项目中一定不 ...

  7. SpringBoot 定时器的三种方式

    SpringBoot 使用定时器的3种方式 1.使用@Scheduled注解定义 @Component public class SimpleSchedule {private Integer tim ...

  8. Springboot定时器多线程解决多个定时器冲突问题

    使用场景 : 我们的订单服务,一般会有一个待支付订单,而这个待支付订单是有时间限制的,比如阿里巴巴的订单是五天,淘宝订单是一天,拼多多订单是一天,美团订单是15分钟- 基金系统中,如何同时更新多个存储 ...

  9. springboot 打卡功能_SpringBoot 动态定时器的使用方法

    SpringBoot使用定时器使用方法添加@Scheduled注解 设计cron参数即可 package com.clsystem.Comm; import org.springframework.s ...

最新文章

  1. 反向区域DNS解析服务
  2. 发现check_nginx.sh 里的一个小bug~~~
  3. 如何解决tmux中Anaconda虚拟环境下的python版本不正确的问题
  4. 计算机视觉与深度学习 | ORB特征提取:基于OpenCV+Python(附代码)
  5. [USACO]地震 (二分答案+最优比率生成树详解)
  6. nginx ci index.php,CI在Nginx服务器上rewrite去掉index.php例子
  7. PHP学习总结(3)——PHP入门篇之PHP的echo语句
  8. E9流程表单中动态自定义添加button js代码
  9. HTML5之2D物理引擎 Box2D for javascript Games 系列 第二部分
  10. Windows程序设计——画圆
  11. SpringBoot+Vue项目个性化音乐推荐系统
  12. 2020年中国洪涝受灾人口数、死亡失踪人口数、倒塌房屋数量及造成的直接经济损失分析[图]
  13. AD7705应用总结:
  14. Linux LED子系统调试与应用 设备树官方文档与 gpio-leds.c 源码详解
  15. unity模型制作(终章):柔体布料绘制
  16. PCBA加工波峰焊空焊原因及对策
  17. 例说hg(四)———— 杂说hg使用场景
  18. 计算机网络交换路由计算,计算机网络 交换路由
  19. 再谈probit回归和logistic回归
  20. [图]实习月薪超过$7000 Glassdoor发布最新实习生工资报告

热门文章

  1. FreeRTOS的学习(六)——系统时钟
  2. 安全证书相关知识补充
  3. Studio One6有哪些新功能及系统配置要求介绍
  4. java开源报表工具JasperReport使用
  5. 数据仓库建模指南系列
  6. 3D打印机或改变世界 可打印出星球大战尤达大师
  7. Loading PDSC Debug Description failed for STMicroelectronics STM32F103ZF Disabling usage of PDSC Deb
  8. matlab 出现错误 an error related to a lxe_win64 or .enc file? enc not exist log Missing Entry: lxe_comm
  9. 荣获创新奖,人大金仓携多款硬核产品亮相CITE2022
  10. ChatGPT中 top_p 和 temperature 的作用机制