【Java】Thread深入学习

本篇文章将介绍Thread类相关方法,以及一些重要概念及应用。JDK提供了直观观察线程状态的工具,在学习线程的过程中,可以使用jconsole命令打开Java监视和管理控制台观察线程运行状态。

【Java】Thread深入学习_第1张图片

1. setDaemon()

守护线程: 当子线程被设置为守护线程时,父线程一旦进入DEAD状态,守护线程也立即进入DEAD状态。示例:

package com.juc;

/**
 * 守护线程: 当被设置为父线程的守护线程时,父线程一旦销毁,子线程也立即销毁。
 * 1. setDaemon(boolean on)必须在线程变成Runnable状态前执行
 * 2. 为维持长连接,需要心跳包,可以将心跳包设置为守护线程,主线程一旦销毁,即不用再发送心跳包维持状态
 */

public class ThreadDaemon {

    public static void main(String[] args) {

        long interval = 2_000L;

        Thread daemonThread = new Thread(() -> {
            Thread innerDaemonThread = new Thread(() -> {
                while (true) {
                    try {
                        Thread.sleep(interval);
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                    System.out.println(Thread.currentThread().getName() + " is alive");
                }
            }, "innerDaemonThread");
            innerDaemonThread.setDaemon(true);
            innerDaemonThread.start();

            while (true) {
                try {
                    Thread.sleep(interval);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                System.out.println(Thread.currentThread().getName() + " is alive");
            }
        }, "daemonThread");

        daemonThread.setDaemon(true);
        daemonThread.start();

        try {
            Thread.sleep(4_000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        System.out.println(Thread.currentThread().getName() + " thread is dead");
    }


}

【Java】Thread深入学习_第2张图片

2. join()

当线程对象使用join()方法后,当前线程所在的父线程将处于BLOCKED状态直到当前线程任务执行完毕。示例:

package com.juc;

import java.util.ArrayList;
import java.util.List;
import java.util.Optional;
import java.util.stream.IntStream;

/**
 * join() 子线程在join()时,父线程会进入blocked状态,直到子线程完成任务,父线程恢复正常
 *
 * Thread.currentThread().join() main会等待main,死循环
 */
public class ThreadJoin {

    public static void main(String[] args) {

        List<Thread> threadList = new ArrayList<>();

        for (int i = 1; i < 4; i++) {
            threadList.add(new ChildThread("childThread" + i));
        }

        threadList.forEach(
                thread -> {
                    thread.start();
                    try {
                        thread.join();
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
        );

        System.out.println("All done.");

    }

}

class ChildThread extends Thread {

    private String threadName;

    public ChildThread(String threadName) {
        this.threadName = threadName;
    }

    @Override
    public void run() {
        IntStream.range(1, 10).forEach( i -> {
            Optional.of(Thread.currentThread().getName() + " " + i).ifPresent(System.out::println);
        });
    }
}

【Java】Thread深入学习_第3张图片

3. interrupt()

线程在执行过程中可以被中断,调用interrupted()查看是否被中断。

package com.juc;

import java.util.Optional;
import java.util.stream.IntStream;

public class ThreadInterrupt {

    public static void main(String[] args) {
        Thread thread = new Thread(()->{
            IntStream.range(1, 10).forEach(
                    i -> {
                        try {
                            Thread.sleep(1_000);
                        } catch (InterruptedException e) {
                             System.out.println("线程被中断 ");
                        }
                        Optional.of(i).ifPresent(System.out::println);
                    }
            );
        }, "thread");

        thread.start();
        try {
            Thread.sleep(2_000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        thread.interrupt();

    }

}

【Java】Thread深入学习_第4张图片

4. setPriority()、线程优先级

package com.juc;

import java.util.Optional;
import java.util.stream.IntStream;

/**
 * @Description Thread类相关的API
 */
public class ThreadAPI {

    public static void main(String[] args) {
        Thread thread1 = new Thread( ()-> {
            printInfo();
        }, "thread1");
        Thread thread2 = new Thread( ()-> {
            printInfo();
        }, "thread2");
        Thread thread3 = new Thread( ()-> {
            printInfo();
        }, "thread3");

        // priority: 优先级的设定有时并无意义,线程能否进入运行状态取决于CPU是否有空闲的时间片
        thread1.setPriority(Thread.MAX_PRIORITY);
        thread2.setPriority(Thread.NORM_PRIORITY);
        thread3.setPriority(Thread.MIN_PRIORITY);

        thread1.start();
        thread2.start();
        thread3.start();
    }

    // id,name: 一般来说,我们创建的第一个线程id为11,前9个是必须线程,第10个是main
    private static void printInfo() {
        Thread c_thread = Thread.currentThread();
        System.out.printf("============%s id: %s===============\n", c_thread.getName(), c_thread.getId());
        IntStream.range(1, 10).forEach(i -> {
            Optional.of(c_thread.getName() + " " + i).ifPresent(System.out::println);
        });
    }

}

【Java】Thread深入学习_第5张图片

你可能感兴趣的:(Java)