https://www.cnblogs.com/wuxun1997/p/6822904.html
定时任务用Timer实现有可能出现异常,因为它是基于绝对时间而不是相对时间进行调度的。当环境的系统时间被修改后,原来的定时任务可能就不跑了。另外需要捕获并处理定时任务抛出的异常。如果在TimerTask里抛出了异常,那么Timer认为定时任务被取消并终止执行线程。举例:
package com.wlf.concurrent;
import java.util.Timer;
import java.util.TimerTask;
public class OutOfTime {
public static void main(String[] args) throws InterruptedException {
Timer timer = new Timer();
// 设置一个一次性的定时任务,1秒后执行
timer.schedule(new PrintTask(), 1000);
// 休眠一秒
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
// 设置一个一次性任务,间隔1秒执行
timer.schedule(new ThrowTask(), 1000);
// 休眠一秒
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
// 再设置一个周期性任务,可是不会再来了
timer.schedule(new PrintTask(), 1000, 1000);
}
static class PrintTask extends TimerTask {
@Override
public void run() {
System.out.println("I'm coming...");
}
}
static class ThrowTask extends TimerTask {
@Override
public void run() {
throw new RuntimeException();
}
}
}
运行结果:
I'm coming...
Exception in thread "Timer-0" java.lang.RuntimeException
at com.wlf.concurrent.OutOfTime$ThrowTask.run(OutOfTime.java:50)
at java.util.TimerThread.mainLoop(Timer.java:555)
at java.util.TimerThread.run(Timer.java:505)
Exception in thread "main" java.lang.IllegalStateException: Timer already cancelled.
at java.util.Timer.sched(Timer.java:397)
at java.util.Timer.schedule(Timer.java:248)
at com.wlf.concurrent.OutOfTime.main(OutOfTime.java:34)
如果注掉这一行,那么定时任务还是会一直跑下去的
timer.schedule(new ThrowTask(), 1000);
或者捕获异常并处理:
static class ThrowTask extends TimerTask {
@Override
public void run() {
try {
throw new RuntimeException();
}catch (Exception e){
System.out.println("I catch the exception");
}
}
}
输出结果: