博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Timer定时器
阅读量:4959 次
发布时间:2019-06-12

本文共 6578 字,大约阅读时间需要 21 分钟。

© 版权声明:本文为博主原创文章,转载请注明出处

1.Timer:有且仅有一个后台线程对多个业务线程进行定时定频率的调度

2.schedule

  schedule(task, time):在时间等于或超过time的时候执行且仅执行一次task

  schedule(task, time, period):时间等于或超过time时首次执行task,之后每隔period毫秒重复执行一次task

  schedule(task, delay):等待delay毫秒后执行且仅执行一次task

  schedule(task, delay, period):等待delay毫秒后首次执行delay,之后每隔period毫秒重复执行一次task

3.scheduleAtFixedRate

  scheduleAtFixedRate(task, time, period):同schedule(task, time, period)

  scheduleAtFixedRate(task, delay, period):同schedule(task, delay, period)

4.schedule和scheduleAtFixedRate区别

  4.1 首次执行的时间早于当前时间

    - schedule会以当前时间为首次执行时间,然后继续执行

package org.timer.test;import java.text.DateFormat;import java.text.SimpleDateFormat;import java.util.Calendar;import java.util.Timer;import java.util.TimerTask;/** * schedule和scheduleAtFixedRate不同 * */public class Difference {	public static void main(String[] args) {				// 获取当前时间		Calendar calendar = Calendar.getInstance();		final DateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");		System.out.println(format.format(calendar.getTime()));				// 创建Timer对象		Timer timer = new Timer();				/**		 * 首次计划执行的时间早于当前时间		 */		// 将时间往前推6s		calendar.add(Calendar.SECOND, -6);				// schedule		timer.schedule(new TimerTask() {						@Override			public void run() {				System.out.println("执行时间为:" + format.format(scheduledExecutionTime()));			}		}, calendar.getTime(), 2000L);			}	}

    - scheduleAtFixedRate仍以计划时间为准,连续执行数次,直至与当前时间相同

package org.timer.test;import java.text.DateFormat;import java.text.SimpleDateFormat;import java.util.Calendar;import java.util.Timer;import java.util.TimerTask;/** * schedule和scheduleAtFixedRate不同 * */public class Difference {	public static void main(String[] args) {				// 获取当前时间		Calendar calendar = Calendar.getInstance();		final DateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");		System.out.println(format.format(calendar.getTime()));				// 创建Timer对象		Timer timer = new Timer();				/**		 * 首次计划执行的时间早于当前时间		 */		// 将时间往前推6s		calendar.add(Calendar.SECOND, -6);				// scheduleAtFixedRate		timer.scheduleAtFixedRate(new TimerTask() {						@Override			public void run() {				System.out.println("执行时间为:" + format.format(scheduledExecutionTime()));			}		}, calendar.getTime(), 2000L);			}	}

  4.2 任务执行所需时间超出任务的执行周期间隔

    - schedule会等待任务执行完成

package org.timer.test;import java.text.DateFormat;import java.text.SimpleDateFormat;import java.util.Calendar;import java.util.Timer;import java.util.TimerTask;/** * schedule和scheduleAtFixedRate不同 * */public class Difference {	public static void main(String[] args) {				// 获取当前时间		Calendar calendar = Calendar.getInstance();		final DateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");		System.out.println(format.format(calendar.getTime()));				// 创建Timer对象		Timer timer = new Timer();				/**		 * 任务执行所需时间超出任务的执行周期间隔		 */		// schedule		timer.schedule(new TimerTask() {						@Override			public void run() {				// 睡眠3s				try {					Thread.sleep(3000);				} catch (InterruptedException e) {					e.printStackTrace();				}				System.out.println("执行时间为:" + format.format(scheduledExecutionTime()));			}		}, calendar.getTime(), 2000L);			}	}

    - scheduleAtFixedRate仍会安装任务的执行周期间隔执行,因此存在并发执行的问题

package org.timer.test;import java.text.DateFormat;import java.text.SimpleDateFormat;import java.util.Calendar;import java.util.Timer;import java.util.TimerTask;/** * schedule和scheduleAtFixedRate不同 * */public class Difference {	public static void main(String[] args) {				// 获取当前时间		Calendar calendar = Calendar.getInstance();		final DateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");		System.out.println(format.format(calendar.getTime()));				// 创建Timer对象		Timer timer = new Timer();				/**		 * 任务执行所需时间超出任务的执行周期间隔		 */		// scheduleAtFixedRate		timer.scheduleAtFixedRate(new TimerTask() {						@Override			public void run() {				// 睡眠3s				try {					Thread.sleep(3000);				} catch (InterruptedException e) {					e.printStackTrace();				}				System.out.println("执行时间为:" + format.format(scheduledExecutionTime()));			}		}, calendar.getTime(), 2000L);			}	}

 5.其他方法

  - scheduleExecutionTime:返回此任务最近实际执行的已安排执行的时间

  - cancel:终止此定时器,丢弃所有当前已安排的任务

  - purge:从此计时器的任务队列中移除所有已取消的任务,并返回从队列中取消的任务数

6.实例  

  需求:创建两个机器人,跳舞机器人和灌水机器人

    - 灌水机器人每隔1s灌一次水,灌满后停止工作

    - 跳舞机器人在水灌满之前每隔2s跳一次舞,水灌满后等待2s,停止工作

  6.1 DancingRobot.java

package org.timer.test;import java.text.DateFormat;import java.text.SimpleDateFormat;import java.util.TimerTask;/** * 跳舞机器人:每隔2s跳一次舞,水灌满后继续跳舞2s然后停止工作 * */public class DancingRobot extends TimerTask {	@Override	public void run() {				// 获取最近的一次任务执行时间,并将其格式化		DateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");		System.out.println("Schedule exec time is : " + format.format(scheduledExecutionTime()));		// 跳舞		System.out.println("Dancing happily!");			}}

  6.2 WaterRobot.java

package org.timer.test;import java.util.Timer;import java.util.TimerTask;/** * 灌水机器人, * @author chen * */public class WaterRoot extends TimerTask {	// 最大容量无5L	private int bucketCapacity = 0;	private Timer timer;		public WaterRoot(Timer timer) {				this.timer = timer;			}	@Override	public void run() {		if (bucketCapacity < 5) {			System.out.println("Add 1L water into the bucket!");			bucketCapacity++;		} else {			System.out.println("The number of canceled task in timer is : " + timer.purge());			// 水满之后停止执行			cancel();			System.out.println("The waterRobot has been aborted");			System.out.println("The number of canceled task in timer is : " + timer.purge());			System.out.println("Current water is : " + bucketCapacity);			// 等待2s,终止timer里面的所有内容			try {				Thread.sleep(2000);			} catch (InterruptedException e) {				e.printStackTrace();			}			timer.cancel();		}			}	}

  6.3 Executor.java

package org.timer.test;import java.text.DateFormat;import java.text.SimpleDateFormat;import java.util.Calendar;import java.util.Timer;public class Executor {	public static void main(String[] args) {				// 创建Timer对象		Timer timer = new Timer();				// 获取当前时间		Calendar calendar = Calendar.getInstance();		DateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");		System.out.println("Current time is : " + format.format(calendar.getTime()));				// 创建两个机器人对象		DancingRobot dr = new DancingRobot();		WaterRoot wr = new WaterRoot(timer);				timer.schedule(dr, calendar.getTime(), 2000L);		timer.scheduleAtFixedRate(wr, calendar.getTime(), 1000L);			}	}

  6.4 效果预览

7.Timer的不足

  7.1 Timer有且仅有一个线程去执行定时任务,如果存在多个任务,且任务时间过长,会导致执行结果与预期不同

  7.2 如果TimerTask抛出RuntimeException,Timer会停止所有任务的运行

  7.3 综上所述:对时效性要求较高的多任务并发作业对复杂的任务调度最好不要使用Timer,可使用Quartz。

参考:

转载于:https://www.cnblogs.com/jinjiyese153/p/6992828.html

你可能感兴趣的文章
大华门禁SDK二次开发(二)-SignalR应用
查看>>
oracle 使用job定时自动重置sequence
查看>>
集成百度推送
查看>>
在项目中加入其他样式
查看>>
在使用Kettle的集群排序中 Carte的设定——(基于Windows)
查看>>
【原】iOS中KVC和KVO的区别
查看>>
OMAPL138学习----DSPLINK DEMO解析之SCALE
查看>>
IoC的基本概念
查看>>
restframework CBV试图的4种方式
查看>>
大图居中,以1920px为例
查看>>
Python3 图片转字符画
查看>>
[C陷阱和缺陷] 第7章 可移植性缺陷
查看>>
人需要治愈
查看>>
linux中configure文件默认执行结果所在位置
查看>>
jmeter 断言
查看>>
Windows向Linux上传文件夹
查看>>
20180104-高级特性-Slice
查看>>
6个SQL Server 2005性能优化工具介绍
查看>>
nginx启动、关闭命令、重启nginx报错open() "/var/run/nginx/nginx.pid" failed
查看>>
day14 Python 内置函数、匿名函数和递归函数
查看>>