线程简述:协程、抢占式、sleep、wait、interrupt,优雅中断线程,线程通信等

思维导图在此:

java 线程 简述-CSDN博客

1、线程与协程

协程-->线程-->进程,协程最小

协程:用户态,go语言

线程:用户态、内核态都有。cpu调度的最小单位。是工人,从进程获取资源,多个线程共享进程的资源。

进程:内核态。操作系统调度资源的最小单位。是资源管家。

2、调度机制

协同式。线程的切换由线程控制。A线程执行完再执行线程B。好处是没有线程同步问题,坏处是A出问题,后面会阻塞。

抢占式。线程的切换由操作系统控制。好处是不会阻塞,坏处是AB不一定谁先执行,且A可能还没执行完就切换到B了,有上下文转换。

java是抢占式,Thread.yeild()可以释放时间片,有上下文切换

3、如何创建线程

start() 和 run()

        // start是thread的方法,创建了线程,并执行runnable任务
        new Thread(runnable).start();
        // run是Runnable的方法,没有创建线程,只执行了任务
        new Thread(() -> System.out.println("只是一个lambda表达式创建的Runnable")).run(); 

4、如何创建任务

Runnable无返回值,不抛出异常

Callable有返回值,抛出异常

Callable底层是Runnable

        Runnable runnable = new Runnable() {
            @Override
            public void run() {
                System.out.println("只是一个Runnable");
            }
        };

        Runnable runnable1 = ()->System.out.println("只是一个lambda表达式创建的Runnable");

        Callable callable = new Callable() {
            @Override
            public Object call() throws Exception {
                return "这是一个callable";
            }
        };

5、java线程本质

java线程绑定jvm的线程(JVM Java Thread),jvm线程绑定操作系统的线程(OS Thread)。然后操作系统线程的状态与jvm线程的状态进行映射绑定

6、线程的几个方法

6.1、想让线程稍等一下

sleep(x):释放时间片(操作系统)、不释放锁(锁与线程无关)。x毫秒后开始竞争时间片

(注意:wait()是Object的方法,释放时间片,释放锁。锁和Object有关,Object中有记录所状态的字段)

yield():就是 sleep(0)

6.2、想让线程执行完再执行当前线程

join():main线程里写了A.join()代码。表示A先参加,即main会阻塞,等A线程执行完,再走main线程

6.3、想让线程停止

stop():释放时间片(马上停止线程),后面的代码不执行,不优雅,不推荐使用

interrupt():“中断”。更改状态,不释放时间片(不会停线程),中断标志位设为true

isInterrupted():“是否中断”。判断中断标志位是否是true

interrupted():“结束中断”。判断中断标志位是否是true,如果是true需要改为false(擦除)

6.4、如何优雅中断线程

  1. 设置中断状态
    使用Thread.interrupt()方法来设置线程的中断状态。这并不会立即停止线程,而是设置了一个中断请求标志。

  2. 检查中断状态
    被中断的线程应该周期性地检查其中断状态,通常通过Thread.currentThread().isInterrupted()方法。

  3. 响应中断
    当线程检测到中断请求时,它应该适当地响应。这通常意味着清理资源、保存状态,并优雅地终止。

  4. 不要使用Thread.stop()
    Thread.stop()方法已经被废弃,因为它可能导致线程留下不一致的状态。应该总是使用中断和协作机制来停止线程。

  5. 处理阻塞操作
    当线程在阻塞操作(如sleep()wait()join(), 或者某些I/O操作)上被中断时,这些操作会抛出InterruptedException。捕获这个异常,清除中断状态(如果需要),并适当地响应中断。

  6. 传递中断
    如果线程在调用其他可中断的阻塞方法时检测到中断,它应该清除自己的中断状态,并设置被调用线程的中断状态,以便后者也能响应中断。

7、线程通信

7.1、两个线程读取同一个变量

volatile:

Java中的volatile_java volatile-CSDN博客

底层:JMM、内存屏障、总线监听与缓存一致性协议

可见性:见到最新的数据。读时工作内存失效,获取主内存。写时工作内存马上刷新到主内存

有序性:和代码书写的顺序一样。禁止cpu优化指令重排。volatile写之前的读写操作不能重排在volatile写之后(和代码逻辑顺序一样)。volatile读之后的读写操作不能重排到volatile读之前(和代码逻辑顺序一样)。

管道:

用的不多

输入流和输出流进行绑定,形成管道。PipedWriter和PipedReader

B里创建管道变量

A = new thread(管道放进去)

B里操作管道变量,A里的管道变量会跟着变,这就实现了AB两个线程的通信,变量共享了,和volatile有点像

7.2、线程之间的阻塞和唤醒

wait()和notify()。Object的方法。涉及到锁,要在synchronize里面用wait,notify唤醒线程。

关键字wait和notify-CSDN博客

join() 、sleelp() 。Thread的方法,底层是wait(),notify()

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值