先定義一個TimerTask類
package lxd.timer.demo;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.TimerTask;
public class MyTimerTask2 extends TimerTask {
private String name;
private long costTime;
public MyTimerTask2(String name, long costTime) {
this.name = name;
this.costTime = costTime;
}
@Override
public void run() {
Calendar calendar = Calendar.getInstance();
SimpleDateFormat sf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
System.out.println(name + "'s current exec time is: "
+ sf.format(calendar.getTime()));
try {
Thread.sleep(costTime);
} catch (InterruptedException e) {
e.printStackTrace();
}
calendar = Calendar.getInstance();
System.out.println(name + "'s finish time is: "
+ sf.format(calendar.getTime()));
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public long getCostTime() {
return costTime;
}
public void setCostTime(long costTime) {
this.costTime = costTime;
}
}
管理併發任務的缺陷
- Timer有且僅有一個線程去執行定時任務,如果存在多個任務,且任務執行時間過長,會導致執行效果與預期不符。
測試demo:
package lxd.timer.demo;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Timer;
/**
*
* Timer的缺陷demo
*
* <pre>
* Timer的缺陷demo,不支持併發
* </pre>
*
* @author 李曉東
*
* 2017.05.28
*
* @since 1.0
*
*/
public class MyTimer2 {
public static void main(String[] args) {
Timer timer = new Timer();
MyTimerTask2 task1 = new MyTimerTask2("No.1", 2000);
MyTimerTask2 task2 = new MyTimerTask2("No.2", 2000);
Calendar calendar = Calendar.getInstance();
SimpleDateFormat sf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
System.out.println("current time is: " + sf.format(calendar.getTime()));
// timer.schedule(task1, calendar.getTime());
// timer.schedule(task2, calendar.getTime());
timer.scheduleAtFixedRate(task1, calendar.getTime(), 2000);
timer.scheduleAtFixedRate(task2, calendar.getTime(), 2000);
}
}
測試結果:
current time is: 2017-05-28 15:58:07
No.1's current exec time is: 2017-05-28 15:58:07
No.1's finish time is: 2017-05-28 15:58:09
No.2's current exec time is: 2017-05-28 15:58:09
No.2's finish time is: 2017-05-28 15:58:11
No.2's current exec time is: 2017-05-28 15:58:11
No.2's finish time is: 2017-05-28 15:58:13
No.1's current exec time is: 2017-05-28 15:58:13
No.1's finish time is: 2017-05-28 15:58:15
No.1's current exec time is: 2017-05-28 15:58:15
以上schedule和scheduleAtFixedRate的效果是一樣的,Timer不支持併發。
當任務拋出異常時的缺陷
- 如果TimerTask拋出RuntimeException,Timer會停止所有任務的運行。
測試demo,在MyTimerTask2的run方法中加上一句話:
@Override
public void run() {
Calendar calendar = Calendar.getInstance();
SimpleDateFormat sf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
System.out.println(name + "'s current exec time is: "
+ sf.format(calendar.getTime()));
try {
Thread.sleep(costTime);
} catch (InterruptedException e) {
e.printStackTrace();
}
calendar = Calendar.getInstance();
System.out.println(name + "'s finish time is: "
+ sf.format(calendar.getTime()));
//加上測試運行時異常
throw new RuntimeException();
}
MyTimer2不變,測試結果:
current time is: 2017-05-28 16:05:35
No.1's current exec time is: 2017-05-28 16:05:35
No.1's finish time is: 2017-05-28 16:05:37
Exception in thread "Timer-0" java.lang.RuntimeException
at lxd.timer.demo.MyTimerTask2.run(MyTimerTask2.java:32)
at java.util.TimerThread.mainLoop(Timer.java:555)
at java.util.TimerThread.run(Timer.java:505)
Timer的使用禁區
- 對時效性要求較高的多任務併發作業
- 對複雜任務的調度
這個時候需要使用Quartz了!