栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

多线程——线程状态及线程常用方法

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

多线程——线程状态及线程常用方法

线程状态

Java中线程的状态分为6种。

    初始(NEW):新创建一个线程对象,但还没有调用start()方法。运行(RUNNABLE):Java线程中将就绪(ready)和运行中(running)两种状态笼统的称为“运行”。
    线程对象创建后,其他线程(比如main线程)调用了该对象的start()方法。该状态的线程位于可运行线程池中,等待被CPU调度,获取CPU的使用权,此时处于就绪状态(ready)。就绪状态的线程在获得CPU时间片后变为运行中状态(running)。阻塞(BLOCKED):表示线程阻塞于锁。等待(WAITING):进入该状态的线程需要等待其他线程做出一些特定动作(通知或中断)。超时等待(TIMED_WAITING):该状态不同于WAITING,它可以在指定的时间后自行返回。终止(TERMINATED):表示该线程已经执行完毕。
    线程状态及状态装换如下图所示
线程常用方法

1、sleep():让出CPU,拥有锁不释放锁(TImedWaiting),可在任意地方调用,不必非得在同步代码中 可以使调用线程睡眠相应的时间,睡足时间后便又回到可运行状态等待CPU调度。
2、yield():** netive静态方法,让出CPU,拥有锁不释放锁,并回到可运行状态(Ready),和其他可运行线程一起等待CPU调度**,可能CPU依旧会调用到该线程。
3、join():使当前线程进入等待状态(Waiting),等待调用线程执行完后才能继续运行,join(time):使得线程在预计时间后和当前线程并行执行(TimeWaiting)
4、wait(): 将当前线程锁释放并进入等待状态(Waiting),wait(time)进入等待状态(TimeWaiting),在等待时间内未被唤醒则自动醒来,防止永久等待,必须在同步方法中调用
5、notify() / notifyAll():唤醒某个(无法确定是哪个线程) / 所有等待中的线程
6、interrupt():打断某个线程(设置中断标志为true),但是不能打断正在竞争锁的线程,如果对调用sleep()、wait()、join()的线程设置标志位会抛异常InterruptedException,必须进行捕获处理。
7、如果想打断线程争抢锁(设置标志位),那么使用ReentrantLock,用锁对象调用lockInterruptibly(),如果有设置标志位则抛异常(InterruptedException)
8、isInterrupted():查询某线程是不是被打断过
9、interrupted():静态方法,当前线程是不是被打断过,如果打断过,并恢复打断标志位false
10、stop():直接暂停线程,释放所有锁,容易产生数据不一致问题,不建议使用(已过时方法)
11、suspend()、resume():暂停线程与恢复线程,容易产生数据不一致问题,不建议使用(已过时方法)

优雅的结束某线程

1、结合interrupt()与( isInterrupted()或interrupted() )方法:达到某条件便设置打断标志位,检查标志位为true结束。(不依赖线程中间状态,针对wait(),sleep()等抛出异常的情况在catch语句块中也可做标志位的检查)

public class ThreadTest {
    public static void main(String[] args) throws InterruptedException {
        Thread t = new Thread(() -> {
            while(true){
                System.out.println("Thread is interrupted ! ");
             System.out.println(Thread.currentThread().isInterrupted());
                if (Thread.currentThread().isInterrupted()) {
                    break;
                }
                
            }
        });
        t.start();
        Thread.sleep(2000L);
        t.interrupt();
    }
}

2、使用Volatile实现优雅结束线程(不依赖于线程的中间状态,Volatile没有啥问题),这里的中间状态比如说:线程中执行装数据,必须装到好多个数据就暂停。但是针对wait()、sleep()等抛异常的情况无法校验running标志。

public class ThreadTest {
    private static volatile boolean running = true;

    private static void m() {
        System.out.println("m start");
        while (running) {
            System.out.println("hello");
        }
        System.out.println("m end!");
    }
    public static void main(String[] args) throws InterruptedException {
        new Thread(Tets::m, "t1").start();
        Thread.sleep(1000L);
        running = false;
    }
}
转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/731698.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号