首页 归档 关于 learn love 工具

java中阻塞和等待状态的区别

首先看java中线程状态轮转图:

可以看到:

  • 阻塞(synchronized)
  • 等待(Object,wait(),Object.join(),LockSupport.park())
  • 超时等待(Thread.sleep(long),Object.wait(long),Thread.join(long),LockSupport.parkNano(),LockSupport.parkUntil())

名称解释

阻塞(BLOCKED)

A thread that is blocked waiting for a monitor lock is in this state.
一个线程因为等待临界区的锁被阻塞产生的状态,synchronize 关键字产生的状态。

等待(WAITING)

A thread that is waiting indefinitely for another thread to perform a particular action is in this state.

当wait,join,park方法调用时,进入waiting状态。前提是这个线程已经拥有锁了。

  • 进入 waiting 状态是线程主动的,而进入 blocked 状态是被动的。
  • 进入 blocked 状态是在同步(synchronized)代码之外,而进入 waiting 状态是在同步代码之内(然后马上退出同步)。

Thread

Thread类里有两个ParkEvent和一个Parker, 其实ParkEvent和Parker实现和功能都类似,只是源码没有重构而已。

  • 一个是给实现synchronized关键字用的;
  • 一个是给Thread.sleep/wait用的;
  • parker是用来实现J.U.C(Unsafe)的park/unpark(阻塞/唤醒);

上面提到,WAITING状态的线程,主要指调用Object,wait(),Object.join(),LockSupport.park()方法的线程操作,其中AQS的挂起,也就是调用LockSupport.park(),恢复则调用LockSupport.unPark()。AQS.Condition.await(),内部也是调用LockSupport.park();

原文

https://giteedev.gitee.io/yyz-coder/2020/08/20/java%E4%B8%AD%E9%98%BB%E5%A1%9E%E5%92%8C%E7%AD%89%E5%BE%85%E7%8A%B6%E6%80%81%E7%9A%84%E5%8C%BA%E5%88%AB%E6%98%AF%E5%95%A5%E7%8E%A9%E6%84%8F%E5%84%BF%EF%BC%9F/