前言

本文隶属于专栏《100个问题搞定Java并发》,该专栏为笔者原创,引用请注明来源,不足和错误之处请在评论区帮忙指出,谢谢!

本专栏目录结构和参考文献请见100个问题搞定Java并发

正文

守护线程

如果你希望创建一个线程来执行一些辅助工作,但又不希望这个线程阻碍JVM的关闭。在这种情况下就需要使用守护线程(Daemon Thread)。

守护线程是一种特殊的线程,就和它的名字一样,它是系统的守护者,在后台默默地完成一些系统性的服务,比如垃圾回收线程、JIT线程就可以理解为守护线程。

用户线程

与之相对应的是用户线程,用户线程可以认为是系统的工作线程,它会完成这个程序应该要完成的业务操作。

如果用户线程全部结束,则意味着这个程序实际上无事可做了。守护线程要守护的对象已经不存在了,那么整个应用程序就应该结束。

因此,当一个Java应用内只有守护线程时,Java虚拟机就会自然退出。

主线程

在JM启动时创建的所有线程中,除了主线程以外,其他的线程都是守护线程。

当创建个新线程时,新线程将继承创建它的线程的守护状态,因此在默认情况下,主线程创建的所有线程都是用户线程。

区别

用户线程与守护线程之间的差异仅在于当线程退出时发生的操作。

当一个线程退出时,JVM会检查其他正在运行的线程,如果这些线程都是守护线程,那么JVM会正常退出操作。

当JVM停止时,所有仍然存在的守护线程都将被抛弃。

实践

创建一个守护线程

package com.shockang.study.java.concurrent.thread.daemon;

import java.util.concurrent.TimeUnit;

public class DaemonDemo {
    public static class DaemonThread extends Thread {
        public void run() {
            for (; ; ) {
                System.out.println("I am alive");
                try {
                    TimeUnit.MILLISECONDS.sleep(1000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        }
    }

    public static void main(String[] args) throws InterruptedException {
        Thread t = new DaemonThread();
        t.setDaemon(true);
        t.start();
        TimeUnit.MILLISECONDS.sleep(2000);
    }
}

控制台输出

/Library/Java/JavaVirtualMachines/jdk1.8.0_192.jdk/Contents/Home/bin/java ...
I am alive
I am alive

Process finished with exit code 0
上一篇 下一篇