zoukankan      html  css  js  c++  java
  • Java多线程之守护线程

    Java多线程之守护线程

    一、前言

    • Java线程有两类:

      • 用户线程:运行在前台,执行具体的任务,程序的主线程,连接网络的子线程等都是用户线程

      • 守护线程:运行在后台,为其他前台线程服务

        • 特点:一旦所有用户线程都结束运行,守护线程会随JVM一起结束工作

        • 应用:数据库连接池中的监测线程JVM启动后的监测线程

        • 最常见的守护线程:垃圾回收线程

        • 如何设置守护线程:可以通过Thread类的setDaemon(true)方法来设置当前的线程为守护线程

    • 注意事项:

      • setDaemon(true)必须在start方法之前调用,否则会抛出IllegalThreadStateException异常

      • 在守护线程中产生的新线程也是守护线程

      • 不是所有的任务都可以分配给守护线程来执行,比如读写操作或者计算逻辑

    二、代码分析:

     1 package me.demo.daemon;
     2 
     3 import java.io.File;
     4 import java.io.FileOutputStream;
     5 import java.io.OutputStream;
     6 import java.util.Scanner;
     7 
     8 class DaemonThread implements Runnable {
     9 
    10     @Override
    11     public void run() {
    12     System.out.println("进入守护线程:" + Thread.currentThread().getName());
    13     try {
    14         WriteToFile();
    15     } catch (Exception e) {
    16         e.printStackTrace();
    17     }
    18     System.out.println("退出守护线程:" + Thread.currentThread().getName());
    19     }
    20 
    21     private void WriteToFile() throws Exception {
    22     File file = new File("E:" + File.separator + "daemon.txt");
    23     // true代表追加操作
    24     OutputStream os = new FileOutputStream(file, true);
    25     int count = 0;
    26     while (count < 999) {
    27         os.write(("
    word" + count).getBytes());
    28         System.out.println("守护线程" + Thread.currentThread().getName() + "向文件中写入了Word" + count++);
    29         Thread.sleep(1000);
    30     }
    31     os.close();
    32     }
    33 
    34 }
    35 
    36 public class DaemonThreadDemo {
    37 
    38     public static void main(String[] args) {
    39     System.out.println("进入主线程:" + Thread.currentThread().getName());
    40     DaemonThread daemonThread = new DaemonThread();
    41     Thread thread = new Thread(daemonThread);
    42     thread.setDaemon(true); // 设为守护线程
    43     thread.start();
    44 
    45     /**
    46      * 主线程阻塞等待键盘输入 由于此时主线程是唯一的用户线程 所以当主线程退出,则守护线程也会退出
    47      * 即while循环提前退出,导致守护线程写入数据的不完整性
    48      */
    49     Scanner input = new Scanner(System.in);
    50     input.next();
    51     input.close();
    52     System.out.println("退出主线程:" + Thread.currentThread().getName());
    53     }
    54 }
    View Code

      运行这个程序,如果我们不做任何操作,他将会向E盘下的daemon.txt文件写入数据,直到while循环结束,并先后打印出退出守护线程和退出主线程字段信息,期间我们如果向控制台输入任意字符串并回车,由于主线程阻塞等待键盘输入,并且此时主线程是唯一的用户线程 所以当主线程退出,则守护线程也会退出,即while循环提前退出,导致守护线程写入数据的不完整性,这正应证了我上面提到的守护线程的特点:一旦所有用户线程都结束运行,守护线程会随JVM一起结束工作

    如果,您认为阅读这篇博客让您有些收获,不妨点击一下右下角的【推荐】。
    如果,您希望更容易地发现我的新博客,不妨点击一下左下角的【关注我】。
    如果,您对我的博文感兴趣,可以关注我的后续博客,我是【AlbertRui】。

    转载请注明出处及链接地址,欢迎转载!

  • 相关阅读:
    16日彻底去除安卓应用的内置广告
    配台600元的主机套装 自己组装 全新
    带记录功能的计算器
    华为8812 进入工程模式 和打电话黑屏问题
    买平板 四核 500~600左右对比
    querySelector()方法
    Javascript实例教程:querySelector()方法接受一个CSS查询并返回匹配模式的第一个子孙元素,如果没有匹配的元素则返回null。
    Android实用代码七段(二)
    Android实用代码七段(三)
    Firebug入门指南
  • 原文地址:https://www.cnblogs.com/albertrui/p/8384189.html
Copyright © 2011-2022 走看看