浅谈java的守护线程与非守护线程

 更新时间:2017年10月13日 11:37:06   作者:super-d2  
这篇文章主要介绍了浅谈java的守护线程与非守护线程,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧

最近重新研究Java基础知识,发现以前太多知识知识略略带过了,比较说Java的线程机制,在Java中有两类线程:User Thread(用户线程)、Daemon Thread(守护线程) ,(PS:以前忽略了)。

估计学过Unix开发但是没有细致学习Java的同学们会疑惑了,操作系统里面是没有所谓的守护线程的概念,只有守护进程一说,但是Java语言机制是构建在JVM的基础之上的,意思是Java平台把操作系统的底层给屏蔽起来,所以它可以在它自己的虚拟的平台里面构造出对自己有利的机制,而语言或者说平台的设计者多多少少是收到Unix思想的影响,而守护线程机制又是对JVM这样的平台凑合,于是守护线程应运而生。

Daemon的作用是为其他线程的运行提供服务,比如说GC线程。其实User Thread线程和Daemon Thread守护线程本质上来说去没啥区别的,唯一的区别之处就在虚拟机的离开:如果User Thread全部撤离,那么Daemon Thread也就没啥线程好服务的了,所以虚拟机也就退出了。

守护线程并非虚拟机内部可以提供,用户也可以自行的设定守护线程,方法:public final void setDaemon(boolean on) ;但是有几点需要注意:

1)、thread.setDaemon(true)必须在thread.start()之前设置,否则会跑出一个IllegalThreadStateException异常。你不能把正在运行的常规线程设置为守护线程。  (备注:这点与守护进程有着明显的区别,守护进程是创建后,让进程摆脱原会话的控制+让进程摆脱原进程组的控制+让进程摆脱原控制终端的控制;所以说寄托于虚拟机的语言机制跟系统级语言有着本质上面的区别)

2)、 在Daemon线程中产生的新线程也是Daemon的。  (这一点又是有着本质的区别了:守护进程fork()出来的子进程不再是守护进程,尽管它把父进程的进程相关信息复制过去了,但是子进程的进程的父进程不是init进程,所谓的守护进程本质上说就是“父进程挂掉,init收养,然后文件0,1,2都是/dev/null,当前目录到/”)

3)、不是所有的应用都可以分配给Daemon线程来进行服务,比如读写操作或者计算逻辑。因为在Daemon Thread还没来的及进行操作时,虚拟机可能已经退出了。

例子:

//完成文件输出的守护线程任务

import java.io.*; 

 

class TestRunnable implements Runnable{ 

  public void run(){ 

        try{ 

         Thread.sleep(1000);//守护线程阻塞1秒后运行 

         File f=new File("daemon.txt"); 

         FileOutputStream os=new FileOutputStream(f,true); 

         os.write("daemon".getBytes()); 

      } 

        catch(IOException e1){ 

     e1.printStackTrace(); 

        } 

        catch(InterruptedException e2){ 

         e2.printStackTrace(); 

      } 

  } 

} 

public class TestDemo2{ 

  public static void main(String[] args) throws InterruptedException 

  { 

    Runnable tr=new TestRunnable(); 

    Thread thread=new Thread(tr); 

        thread.setDaemon(true); //设置守护线程 

    thread.start(); //开始执行分进程 

  } 

} 

运行结果:文件daemon.txt中没有"daemon"字符串。

但是如果把thread.setDaemon(true); //设置守护线程注释掉,文件daemon.txt是可以被写入daemon字符串的

 

JRE判断程序是否执行结束的标准是所有的前台执线程行完毕了,而不管后台线程的状态,因此,在使用后台线程候一定要注意这个问题。

但是daemon Thread实际应用在那里呢?举个例子,web服务器中的Servlet,容器启动时后台初始化一个服务线程,即调度线程,负责处理http请求,然后每个请求过来调度线程从线程池中取出一个工作者线程来处理该请求,从而实现并发控制的目的。

网上摘的一个图,方便大家理解:

 

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持脚本之家。

相关文章

  • Java中用户向系统传递参数的三种基本方式实例分享

    Java中用户向系统传递参数的三种基本方式实例分享

    这篇文章主要介绍了Java中用户向系统传递参数的三种基本方式实例,有需要的朋友可以参考一下
    2014-01-01
  • intellij idea查看方法被哪些类引用过(推荐)

    intellij idea查看方法被哪些类引用过(推荐)

    这篇文章主要介绍了intellij idea查看方法被哪些类引用过,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2020-08-08
  • 解读yml文件中配置时间类型的转换方式

    解读yml文件中配置时间类型的转换方式

    这篇文章主要介绍了yml文件中配置时间类型的转换方式,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2023-12-12
  • Java报错java.awt.AWTException: AWT的解决方法

    Java报错java.awt.AWTException: AWT的解决方法

    在Java图形用户界面(GUI)编程中,java.awt.AWTException是一个常见的异常,它通常与AWT(Abstract Window Toolkit)组件相关,这个异常可能在尝试进行与窗口、图形环境或系统剪贴板等操作时抛出,本文将详细探讨AWTException的成因,并提供多种解决方案
    2024-12-12
  • java web中图片验证码功能的简单实现方法

    java web中图片验证码功能的简单实现方法

    下面小编就为大家带来一篇java web 验证码的简单实现方法。小编觉得挺不错的,现在就分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2016-06-06
  • Spring boot进行参数校验的方法实例详解

    Spring boot进行参数校验的方法实例详解

    这篇文章主要介绍了Spring boot进行参数校验的方法实例详解,非 常不错,具有参考借鉴价值,需要的朋友参考下吧
    2018-05-05
  • springMVC几种页面跳转方式小结

    springMVC几种页面跳转方式小结

    本篇文章主要介绍了springMVC 几种页面跳转方式,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2017-02-02
  • Spring循环依赖的解决方案详解

    Spring循环依赖的解决方案详解

    这篇文章将用实例为大家详细介绍了介绍如何解决Spring的循环依赖问题,文中的示例代码讲解详细,对我们学习Spring有一定的帮助,需要的可以参考一下
    2022-07-07
  • SpringBoot整合EasyExcel实现批量导入导出

    SpringBoot整合EasyExcel实现批量导入导出

    这篇文章主要为大家详细介绍了SpringBoot整合EasyExcel实现批量导入导出功能的相关知识,文中的示例代码讲解详细,需要的小伙伴可以参考下
    2024-03-03
  • Spring Boot自动配置源码实例解析

    Spring Boot自动配置源码实例解析

    Spring Boot作为Java领域最为流行的快速开发框架之一,其核心特性之一就是其强大的自动配置机制,下面这篇文章主要给大家介绍了关于Spring Boot自动配置源码的相关资料,文中通过代码介绍的非常详细,需要的朋友可以参考下
    2024-08-08

最新评论