Java的线程分为两种,一个是用户线程,一个是守护线程。守护线程守护的对象就是用户线程,当用户线程结束后,守护它的守护线程也就会结束。二者的本质基本是一样的,唯一区别在于何时结束。

  • 用户线程:直到自己运行完或者遇到异常就结束
  • 守护线程:生命周期伴随着用户线程,随着用户线程结束而结束。

举个例子:运行状态的日志线程一般为守护线程,它时时记录运行状态的日志,守护着系统的主线程。当主线程结束或出现异常结束后,记录日志的守护线程就没有必要在记录,随着主线程结束而结束。

在java中将用户线程变为守护线程,调用setDaemon方法。

 package com.my.day01.demo05;

 public class DaemoTest {

     public static void main(String[] args) {

         Thread t = new Thread(new Runnable() {

             @Override
public void run() { try { System.out.println(Thread.currentThread().getName()+" running");
Thread.sleep(2000);
System.out.println("test");
System.out.println(Thread.currentThread().getName()+" done"); } catch (InterruptedException e) { e.printStackTrace();
}
}
});
//设置为非守护线程,随着main线程的结束,守护线程也结束
t.setDaemon(false);
t.start(); System.out.println(Thread.currentThread().getName());
} }
结果为:
main
Thread-0 running
test
Thread-0 done

在这个例子中,线程t为非守护线程,那么在main线程执行完后,线程t仍在执行。从输出的结果就可以看出来。

将线程t设为守护线程再来看一下

 package com.my.day01.demo05;

 public class DaemoTest {

     public static void main(String[] args) {

         Thread t = new Thread(new Runnable() {

             @Override
public void run() { try { System.out.println(Thread.currentThread().getName()+" running");
Thread.sleep(2000);
System.out.println("test");
System.out.println(Thread.currentThread().getName()+" done"); } catch (InterruptedException e) { e.printStackTrace();
}
}
});
//设置为守护线程,随着main线程的结束,守护线程也结束
t.setDaemon(true);
t.start(); System.out.println(Thread.currentThread().getName());
} }
结果为:
main
Thread-0 running

将线程设置为守护线程后,可以看到线程t没有运行完毕就随着main线程的结束而结束了。

再来看嵌套线程的守护线程,在main函数里面声明了一个名字叫Thread1的线程,在Thread1线程里面定义了一个名字为Thread2的线程。先将这个两个线程设为非守护线程,看结果。

 package com.my.day01.demo05;

 public class DaemoTest2 {

     public static void main(String[] args) {

         Thread t = new Thread(new Runnable() {
@Override
public void run() { Thread tt = new Thread(new Runnable() {
@Override
public void run() {
System.out.println(Thread.currentThread().getName() + "running");
try {
Thread.sleep(20_000);
} catch (InterruptedException e) { e.printStackTrace();
}
System.out.println(Thread.currentThread().getName() + "done");
} }, "Thread2"); tt.setDaemon(false);
tt.start(); System.out.println(Thread.currentThread().getName() + "running");
try { Thread.sleep(10_000); } catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println(Thread.currentThread().getName() + "done");
}
}, "Thread1"); // 设置为非守护线程,随着main线程的结束,守护线程也结束
t.setDaemon(false);
t.start(); System.out.println(Thread.currentThread().getName()); }
}
结果:
main
Thread1running
Thread2running
Thread1done
Thread2done

main线程执行完后,Thread2和Thread1交替执行。再来看看将子线程Thread2设为守护线程,输出的结果为

 main
Thread1running
Thread2running
Thread1done

可以看到子线程Thread2守护Thread1,当Thread1结束后,Thread2也随之结束。

如果将线程Thread1也设置为守护线程,再来看结果

main

Thread1守护的是main线程,main线程一结束Thread1也随之结束。Thread1的子线程Thread2也跟着结束(这就是说守护线程具有继承性,如果一个线程为守护线程,那么它的子线程都为守护线程)

总结:

1.守护线程守护的是它所在声明的那个线程。

2.当指定一个线程为守护线程后,它的子线程都是守护线程。

Java多线程编程之守护线程的更多相关文章

  1. java并发编程学习: 守护线程(Daemon Thread)

    在正式理解这个概念前,先把 守护线程 与 守护进程 这二个极其相似的说法区分开,守护进程通常是为了防止某些应用因各种意外原因退出,而在后台独立运行的系统服务或应用程序. 比如:我们开发了一个邮件发送程 ...

  2. java 多线程8(守护线程)

    比如:后台偷偷运行的那些,qq下载更新包 如果一个进程中只剩下了守护线程,那么守护线程也会死亡.. 一个线程默认都不是守护线程. 判断是否是守护线程:例:d.isDaemon(); 当一个线程随着你的 ...

  3. JAVA多线程学习六-守护线程

    java中的守护程序线程是一个服务提供程序线程,它为用户线程提供服务. 它的生命依赖于用户线程,即当所有用户线程都死掉时,JVM会自动终止该线程. 有许多java守护程序线程自动运行,例如 gc,fi ...

  4. java多线程编程(二创建线程)

    1.概念           因为java是完全面向对象的,所以在java中,我们说的线程,就是Thread类的一个实例对象.所以,一个线程就是一个对象,它有自己字段和方法. 2.创建线程 创建线程有 ...

  5. Java多线程编程(1)--Java中的线程

    一.程序.进程和线程   程序是一组指令的有序集合,也可以将其通俗地理解为若干行代码.它本身没有任何运行的含义,它只是一个静态的实体,它可能只是一个单纯的文本文件,也有可能是经过编译之后生成的可执行文 ...

  6. Java多线程编程(4)--线程同步机制

    一.锁 1.锁的概念   线程安全问题的产生是因为多个线程并发访问共享数据造成的,如果能将多个线程对共享数据的并发访问改为串行访问,即一个共享数据同一时刻只能被一个线程访问,就可以避免线程安全问题.锁 ...

  7. 《java多线程编程核心技术》不使用等待通知机制 实现线程间通信的 疑问分析

    不使用等待通知机制 实现线程间通信的 疑问分析 2018年04月03日 17:15:08       ayf 阅读数:33 编辑 <java多线程编程核心技术>一书第三章开头,有如下案例: ...

  8. Java多线程编程-线程之间的通信

    转载自:这里 学习了基础的线程知识 看到了 线程之间的通信 线程之间有哪些通信方式呢? 1.同步 这里讲的同步是指多个线程通过synchronized关键字这种方式来实现线程间的通信. public ...

  9. Java—多线程编程

    一个多线程程序包含两个或多个能并发运行的部分.程序的每一部分都称作一个线程,并且每个线程定义了一个独立的执行路径. 进程:一个进程包括由操作系统分配的内存空间,包含一个或多个线程.一个线程不能独立的存 ...

随机推荐

  1. [ DLPytorch ] 批量归一化与残差网络

    批量归一化 通常来说,数据标准化预处理对于浅层模型就足够有效了.随着模型训练的进行,当每层中参数更新时,靠近输出层的输出较难出现剧烈变化.但对深层神经网络来说,即使输入数据已做标准化,训练中模型参数的 ...

  2. office 格式定义

    在做项目中,碰到如题的问题.比如要将居民的信息导出到excel中,居民的身份证号码因为长度过长(大于10位),excel会自动的将过长的数字串转换成 科学计数法.现在网上找到解决方案之一: (在数字串 ...

  3. paramiko linux pip18.1

    Collecting paramiko Downloading https://files.pythonhosted.org/packages/cf/ae/94e70d49044ccc234bfdba ...

  4. redhat 7.6 流量监控命令、软件(2) iftop 监控网络IP实时流量

    1.安装iftop,先要安装flex.bison.libpcap编译安装 解压红箭头的两个文件 tar  -zxvpf  iftop-0.16.tar.gz tar  -zxvpf   libpcap ...

  5. 包装类和toString和static关键字

    包装类 针对八种基本数据类型定义的引用类型. 有类的特点,可以调用类中的方法. 基本数据类型 包装类 boolean Boolean byte Byte short Short int Integer ...

  6. 循环语句(while语句和do...while语句)

    1.while语句:如果条件成立,就继续循环,直到条件不成立为止.格式如下: while (条件) {               循环体(语句或语句块) } 2.do…while语句:如果条件成立, ...

  7. C++:面向对象的相关概念

    对象: 一般意义上的对象:是现实世界中一个实际存在的事物 面向对象方法中的对象:是系统中用来描述客观事物的一个实体 抽象与分类: 分类所依据的原则:抽象 抽象出同一类对象的共同属性和行为,形成类 类与 ...

  8. Java基础 -3.2

    逻辑运算符 三目(赋值)运算符 合理地利用三目运算可以避免一些大范围的程序编写 三目运算是一种所谓的赋值运算的处理 它是需要设置一个逻辑关系的判断之后才可以进行的赋值操作 基本语法: 关系运算?关系满 ...

  9. python中sys和os的区别

    <os和sys的官方解释> ➤os os: This module provides a portable way of using operating system dependent ...

  10. js中数值各进制之间的转换

    十进制转换为二进制 toString()方法可把一个 Number 对象转换为一个字符串,并返回结果.语法如下: NumberObject.toString(radix); 其中,radix为可选.规 ...