线程状态
Java中线程状态有六种,定义在Thread类中的State枚举类中
NEW:初始状态,线程创建之后还没有开始运行。RUNNABLE:可运行状态,线程正在运行或者已经就绪等待CPU资源。BLOCKED:阻塞状态,因为竞争锁而发生阻塞。WAITING:等待状态,线程等待其他线程执行特定的动作。TIMED_WAITING:计时等待状态,TERMINATED:终止状态,线程已经执行结束。
线程状态转换
根据线程状态转换图,来详细介绍不同状态的转换方式
① NEW -> RUNNABLE
- 调用线程的
start()方法后,状态由NEW转换成RUNNABLE
② RUNNABLE -> WAITING
以下几种情况需要注意进入
WAITING状态的是哪个线程
- 线程
t通过synchronized(obj)获取到对象锁后调用obj.wait()方法时,t线程从RUNNABLE转换为WAITING - 调用
t.join()、LockSupport.park()方法,当前线程状态由RUNNABLE转换成WAITING
③ WAITING -> RUNNABLE
基于②的情况,调用obj.notify()、obj.notifyAll()、t.interrupt()方法时
- 竞争锁成功,状态由
WAITING转换为RUNNABLE - 竞争锁失败,状态由
WAITING转换为BLOCKED,对应图中⑧的状态
或者调用LockSupport.unpark(t)方法时,t线程状态会由WAITING转换为RUNNABLE
④ RUNNABLE -> TIMED_WAITING
这里同样需要注意发生状态转换的是哪个线程
- 线程
t通过synchronized(obj)获取到对象锁后调用obj.wait(timeout)方法时,t线程从RUNNABLE转换为TIMED_WAITING - 调用
Thread.sleep(timeout)、t.join(timeout)、LockSupport.parkNanos(timeout)、LockSupport.parkUntil(timeout)时,当前线程状态由RUNNABLE转换为TIMED_WAITING
⑤ TIMED_WAITING -> RUNNABLE
基于④的情况下,当调用obj.notify()、obj.notifyAll()、t.interrupt()方法时,
- 竞争锁成功,状态由
TIMED_WAITING转换为RUNNABLE - 竞争锁失败,状态由
TIMED_WAITING转换为BLOCKED,对应图中⑨的状态
调用LockSupport.unpark()方法或者线程等待时间到了,状态由TIMED_WAITING转换为RUNNABLE
⑥ RUNNABLE -> BLOCKED
当线程尝试获取synchronized对象锁时,如果竞争失败,线程状态会由RUNNABLE转换为BLOCKED
⑦ BLOCKED -> RUNNABLE
当持有synchronized对象锁的线程执行完毕,会唤醒处于BLOCKED状态的锁重新竞争,如果t线程竞争成功,状态会由BLOCKED转换为RUNNABLE
⑩ RUNNABLE -> TERMINATED
线程任务执行完毕,状态由 RUNNABLE转换为TERMINATED