Java-DaemonThread

守护线程与普通线程

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
public class DaemonThreadTest {

public static void main(String[] args) {
//TODO 守护线程(sleep 6s)
Thread thread1 = new Thread(){
@Override
public void run() {
try {
Thread.sleep(6000);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println(1);
}
};
thread1.setDaemon(true);


//TODO 普通线程(sleep 1s)
Thread thread2 = new Thread(){

@Override
public void run() {
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("thread-"+2);
}
};

thread2.start();
thread1.start();

// 普通线程执行完后,守护线程就自动结束了(没有输出了)

}

}

demon-thread(守护线程),在jvm检测到没有前台(普通)线程运行时,就会自动终止守护线程;
(把daemon线程当做普通线程很危险,因为不知道什么时候就会终止掉了)

如果还有一个或以上的非守护线程则JVM不会退出(这也是有的web应用无法被shutdown的原因吧)

应用

GC垃圾回收器

gc线程就是一个daemon-thread,有其他线程运行时它是正常处理(回收内存垃圾);
当jvm终止前检查到没有普通线程运行时,就会自动终止gc线程。

web容器(tomcat)

  1. tomcat启动时整个进程会使用socket阻塞在8005端口,参考org.apache.catalina.core.StandardServer#await;收到SHOWDOWN信号后停止主线程org.apache.catalina.startup.Catalina#stopServer

  2. (Java中守护线程的总结)[https://blog.csdn.net/shimiso/article/details/8964414]