Java 守护线程的作用 Java 守护线程线程

一、概述

        在看java线程相关的内容时,有一个 daemon thread 守护线程的概念,看方法注释内容,大意是:将此线程标记为守护线程用户线程。当运行的所有线程都是守护线程时,Java虚拟机将退出


Marks this thread as either a daemon thread or a user thread.
 The Java Virtual Machine exits when the only threads running are all daemon threads.

 

 

二、守护线程理解

        1、有这么一段代码:

public static void main(String[] args) {
    Thread mainThread = Thread.currentThread();
    System.out.println(mainThread.getName() +" mainThread daemon :" + mainThread.isDaemon());

    Thread thread = new Thread(() -> {
        int res = new Random().nextInt(1000);
        try {
            Thread.sleep(res);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        System.out.println(Thread.currentThread().getName() + "==》》res=" + res);
    });
    thread.setDaemon(true);
    thread.start();
    System.out.println("daemon : " + thread.isDaemon());
    System.out.println(Thread.currentThread().getName() + "==》程序执行完毕!");
}

        2、 thread.setDaemon(true); 时,结果如下 (异步线程没有执行):

main mainThread daemon :false
daemon : true
main==》程序执行完毕!

        3、thread.setDaemon(false); 时,结果如下(异步线程有结果):

main mainThread daemon :false
daemon : false
main==》程序执行完毕!
Thread-0==》》res=102

        4、结论:当前 thread.setDaemon(true); 时,通过控制台的输出,我们可以看到 当线程被设置为守护线程后,此时程序中没有正在执行的 非守护线程,程序就会执行结束 --- 异步线程比 main线程晚2秒执行,此时 main线程已经执行完毕。

三、总结

        1、java中线程默认都是非守护线程,即 daemon = false ,可以通过 thread.setDaemon(true); 设置为守护线程。

        2、thread.setDaemon(true) 必须在 thread.start() 之前设置,否则会抛出 IllegalThreadStateException 异常。

        3、在使用 junit 单元测试时,会出现: 无论线程是否为 守护线程,异步线程都不会执行 --- 不确定啥问题, 估计是 junit 单元测试的问题 。

        4、比如下面这段代码:子线程内容不会执行的!

@Test
public void daemonNotest() throws Exception{
    Thread unitTestThread = Thread.currentThread();
    System.out.println(unitTestThread.getName() +" unitTestThread daemon :" + unitTestThread.isDaemon());

    Thread thread = new Thread(() -> {
        int res = new Random().nextInt(1000);
        try {
            Thread.sleep(1000L);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        System.out.println(Thread.currentThread().getName() + "==》》res=" + res);
    });
    System.out.println("daemon : " + thread.isDaemon());
    thread.start();
    System.out.println(Thread.currentThread().getName() + "==》程序执行完毕!");
}

        5、多线程相关的测试,请 使用 main 方法,比较好!经验之谈,不确定 Junit 是啥原因导致不执行!

Logo

华为开发者空间,是为全球开发者打造的专属开发空间,汇聚了华为优质开发资源及工具,致力于让每一位开发者拥有一台云主机,基于华为根生态开发、创新。

更多推荐