详解Java线程中常用操作

 更新时间:2022年05月18日 09:53:02   作者:渊渟岳  
这篇文章主要为大家详细介绍了一下Java线程中的一些常用操作,文中的示例代码讲解详细,对我们学习或工作有一定帮助,需要的可以参考一下

线程的常用操作

设置线程名字:setName()

获取线程名称:getName()

线程唯一Id:getId()

// 自定义线程名称
String threadName = "threadName";
// 构造方法方式
Thread thread = new Thread(() -> {
    System.out.println("线程名=" + Thread.currentThread().getName());
},threadName);
// set方法方式
// thread.setName(threadName);
System.out.println("线程唯一Id=" + thread.getId());

线程启动:start()

判断线程是否存活:isAlive()

// 线程启动
thread.start();
System.out.println("是否为存活线程=" + thread.isAlive());

线程方法:run() /call()

线程启动后会去调用的方法。线程要做什么就在run/call方法写,不需要直接调用,线程启动后自己会去调用run() /call()。如果程序没有启动线程直接调用run/call,那么就不属于多线程编程,是属于当前线程直接调用普通方法一样。

获取当前线程对象:currentThread()

操作当前线程的非static方法,得先拿到线程对象才可以

// 获取当前线程对象
Thread currentThread = Thread.currentThread();
// 对当前线程做一些操作
System.out.println(currentThread.getName());
try {
    // sleep 静态方法则不需要
    Thread.sleep(1000);
} catch (InterruptedException e) {
    e.printStackTrace();
}

关于线程的状态控制(生命周期)的操作可以参考上一篇文章。

守护线程(后台线程)

普通线程(用户线程)的守护者,守护线程的任务是为其他的线程提供服务。如果进程中没有了用户线程,那么守护线程也就没有存在的意义,JVM也随之结束。典型的守护线程有JVM的垃圾回收线程,操作系统的启动也会启动各种模块的守护线程。

设置线程为守护线程:setDaeman()

注意:该方法必须在start() 方法之前调用

public static void main(String[] args) {
    Thread thread = new Thread(() -> {
        System.out.println("线程名="+Thread.currentThread().getName());
        try {
            Thread.sleep(1000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        // 这一句不会打印出来,因为main线程(目前唯一的普通线程)等待1秒后已经结束了
        System.out.println("守护线程的状态=" + Thread.currentThread().getState());
    });
    // 守护线程
    thread.setDaemon(true);
    // 线程启动
    thread.start();
    System.out.println("是否为守护线程=" + thread.isDaemon());
}

线程串行化

执行join() 方法的线程进入等待唤醒状态(WAITING),直到调用该方法的线程结束后再由等待唤醒状态转为可运行状态(RUNNABLE)。join() 方法是Thread类中的方法,其底层是使用wait() 方法来实现线程等待,待线程isAlive()为false 时才

实现线程的串行化:一个线程调用另一个线程对象的join() 来实现线程串行化执行。

举个例子:一道好菜

public class DemoCooking {
    
    public static void main(String[] args) {
        Thread mainThread = Thread.currentThread();
        // 1.买菜
        Thread buyThread = new Thread(new CookingThread(mainThread,"买菜"),"buyThread");
        // 2.洗菜
        Thread washThread = new Thread(new CookingThread(buyThread,"洗菜"),"washThread");
        // 3.切菜
        Thread cutThread = new Thread(new CookingThread(washThread,"切菜"),"cutThread");
        // 4.炒菜
        Thread scrambleThread = new Thread(new CookingThread(cutThread,"炒菜"),"scrambleThread");

        // 不受线程启动顺序的影响
        scrambleThread.start();
        washThread.start();
        cutThread.start();
        buyThread.start();
        
        // main线程先执行完才可以开始:买菜
        System.out.println("开始准备……");
    }

    public static class CookingThread implements Runnable{
        private final Thread thread;
        private final String job;

        public CookingThread(Thread thread, String job){
            this.thread = thread;
            this.job = job;
        }
        @Override
        public void run() {
            String name = Thread.currentThread().getName()+":";
            try {
                thread.join();

                System.out.println(name + job + "开始");
                Thread.sleep(1000);
                System.out.println(name + job + "结束");
                Thread.sleep(1000); // 偷懒下
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }
}

执行结果:main > buyThread > washThread > cutThread > scrambleThread > 结束

开始准备……
buyThread:买菜开始
buyThread:买菜结束
washThread:洗菜开始
washThread:洗菜结束
cutThread:切菜开始
cutThread:切菜结束
scrambleThread:炒菜开始
scrambleThread:炒菜结束

线程优先级

设置当前线程的优先级,线程优先级越高,线程可能获得执行的次数越多,Java线程的优先级用整数表示,优先级的范围为1-10,默认为5。

setPriority(int)方法:设置线程的优先级。

getPriority方法:获取线程的优先级。

public static void main(String[] args) {

    Thread thread = new Thread(() -> {
        System.out.println("线程1");
    });
    thread.setPriority(10);
    Thread thread1 = new Thread(() -> {
        System.out.println("线程2");
    });
    thread1.setPriority(1);
    thread.start();
    thread1.start();

    System.out.println("线程默认的优先级为=" + Thread.currentThread().getPriority());

}

线程中断

使用interrupt() 方法设置线程中断标志=true,让线程受到“阻塞”时抛出一个中断信号。如果线程处于阻塞、等待唤醒或超时等待状态(Object.wait, Thread.join和Thread.sleep)时,那么它将接收到一个中断异常(InterruptedException),从而提前被结束该状态。反之,如果线程是处于“可运行”(RUNNABLE)状态,那么中断标志将没有作用。

案例一:线程中断有效

public static void main(String[] args) {
    Thread thread = new Thread(() -> {
        System.out.println("线程1");
        try {
            // 闹钟1分钟后响
            Thread.sleep(60000);
            System.out.println("闹钟响了");
        } catch (InterruptedException e) {
            // 提前退出超时等待状态
            System.out.println("发生异常,提前醒了,闹钟没响手动关了");
        }

        System.out.println("继续执行该线程的后续程序……");

    });
    thread.setPriority(1);
    thread.start();
    thread.interrupt();
    System.out.println("main线程将thread 终端状态设置为 "+thread.isInterrupted());
}

执行结果:

main线程将thread 终端状态设置为 true
线程1
发生异常,提前醒了,闹钟没响手动关了
继续执行该线程的后续程序……

案例二:线程中断无效

public static void main(String[] args) {
    Thread thread1 = new Thread(() -> {
        System.out.println("线程" + Thread.currentThread().getName());
        while (true) {
            System.out.print(Thread.currentThread().getState() + "\t");
        }
    });
    thread1.start();
    thread1.interrupt();
}

执行结果:线程一直打印自己的状态为RUNNABLE。

以上就是详解Java线程中常用操作的详细内容,更多关于Java线程操作的资料请关注脚本之家其它相关文章!

相关文章

  • springboot 1.5.2 集成kafka的简单例子

    springboot 1.5.2 集成kafka的简单例子

    本篇文章主要介绍了springboot 1.5.2 集成kafka的简单例子 ,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2017-11-11
  • Java中的ReentrantLock使用解析

    Java中的ReentrantLock使用解析

    这篇文章主要介绍了Java中的ReentrantLock使用解析,ReentrandLock即可重入锁,可重入锁解决的是重入锁定的问题,重入锁定指的是当一个线程执行逻辑时,需要两次获取锁,而该锁不可重入就会导致内部嵌套无法获取锁导致Reentrance Lockout发生,需要的朋友可以参考下
    2023-11-11
  • java Scanner输入数字、字符串过程解析

    java Scanner输入数字、字符串过程解析

    这篇文章主要介绍了java Scanner输入数字、字符串过程解析,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下
    2019-10-10
  • Java实现文件监控器FileMonitor的实例代码

    Java实现文件监控器FileMonitor的实例代码

    这篇文章主要介绍了Java实现文件监控器FileMonitor的实例代码,非常不错,具有一定的参考借鉴价值,需要的朋友可以参考下
    2019-12-12
  • java 实现当前时间加减30分钟的时间代码

    java 实现当前时间加减30分钟的时间代码

    这篇文章主要介绍了java 实现当前时间加减30分钟的时间代码,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧
    2020-08-08
  • java类的加载过程以及类加载器的分析

    java类的加载过程以及类加载器的分析

    这篇文章给大家详细讲述了java类的加载过程以及类加载器的相关知识点内容,有需要的朋友可以学习下。
    2018-08-08
  • mybatis中foreach嵌套if标签方式

    mybatis中foreach嵌套if标签方式

    这篇文章主要介绍了mybatis中foreach嵌套if标签方式,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2022-03-03
  • Intellij IDEA调试技巧的深入讲解

    Intellij IDEA调试技巧的深入讲解

    这篇文章主要给大家介绍了关于Intellij IDEA调试技巧的相关资料,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面来一起学习学习吧
    2019-08-08
  • 区块链java代码实现

    区块链java代码实现

    这篇文章主要为大家详细介绍了区块链java代码实现,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2018-01-01
  • Java中的自旋锁spinlock详解

    Java中的自旋锁spinlock详解

    这篇文章主要介绍了Java中的自旋锁spinlock详解,自旋锁就是循环尝试获取锁,不会放弃CPU时间片,减伤cup上下文切换,缺点是循环会消耗cpu,需要的朋友可以参考下
    2024-01-01

最新评论