【问题标题】:Java program never quits after scheduling and running a TimerTaskJava 程序在调度和运行 TimerTask 后从不退出
【发布时间】:2013-05-23 20:51:00
【问题描述】:
我有这个简单的 Java 代码,它应该安排一些东西在 1 毫秒内运行然后退出。
import java.util.*;
class A {
public static void main(String[] args) {
new Timer().schedule(new TimerTask() {
public void run() {
System.out.println("hello");
}
}, 1);
System.out.println("hi");
}
}
它永远不会退出。为什么?
$ javac A.java && java A
hi
hello
如果我删除设置时间表的代码,它会起作用。为什么?
【问题讨论】:
标签:
java
scheduling
deadlock
【解决方案1】:
documentation of java.util.Timer 说:
如果调用者想要快速终止定时器的任务执行线程,调用者应该调用定时器的取消方法。
这是你应该做的。 Robert Harvey 链接到一些内容,该内容将向您显示如何作为您问题下方的评论。
使用您的代码,打印的内容与您的代码相同,但随后退出:
public static void main(String[] args) {
final Timer timer = new Timer();
timer.schedule(new TimerTask() {
public void run() {
System.out.println("hello");
timer.cancel();
}
}, 1);
System.out.println("hi");
}
或者,您可以像这样创建计时器,使其成为守护进程:
public static void main(String[] args) {
final Timer timer = new Timer(true);
timer.schedule(new TimerTask() {
public void run() {
System.out.println("hello");
}
}, 1);
System.out.println("hi");
}
问题是这可以在任务运行之前退出并给出如下输出:
hi
<exit>
public Timer(boolean isDaemon) 的 javadoc 解释了原因:
创建一个新的计时器,其关联的线程可以指定为作为守护进程运行。如果计时器将用于安排重复的“维护活动”,则调用守护线程,只要应用程序正在运行,就必须执行此操作,但不应延长应用程序的生命周期。