1.五種狀态(作業系統角度)
以下是從作業系統層面來描述的
**[初始狀态]**僅是在語言層面建立 了線程對象, 還未與作業系統線程關聯.
[可運作狀态] (就緒狀态)指該線程已經被建立(與作業系統線程關聯), 可以由CPU排程執行
[運作狀态]
指擷取了CPU時間片運作中的狀态
當CPU時間片用完,會從[運作狀态]轉換至[可運作狀态],會導緻線程的上下文切換
如果調用了阻塞API,如BIO讀寫檔案,這時該線程實際不會用到CPU,會導緻線程上下文切換
[阻塞狀态]
等BIO操作完畢,會由作業系統喚醒阻塞的線程,轉換至[可運作狀态]
與[可運作狀态]的差別是,對[阻塞狀态]的線程來說隻要它們一-直不喚醒,排程器就-直不會考慮排程它們
[終止狀态]
表示線程已經執行完畢,生命周期已經結束,不會再轉換為其它狀态
2.六種狀态(API層面)
這是Java API層面來描述的
根據Thread State枚舉,分為六種狀态
public enum State {
NEW,
RUNNABLE,
BLOCKED,
WAITING,
TIMED_WAITING,
TERMINATED;
}
NEW 線程剛被建立,但是還沒有調用 start() 方法
RUNNABLE 當調用了 start() 方法之後,注意,Java API 層面的 RUNNABLE 狀态涵蓋了 作業系統 層面的【可運作狀态】、【運作狀态】和【阻塞狀态】(由于 BIO 導緻的線程阻塞,在 Java 裡無法區分,仍然認為是可運作)
BLOCKED , WAITING , TIMED_WAITING 都是 Java API 層面對【阻塞狀态】的細分,
BLOCKED:線程拿不到鎖,進入阻塞态,如synchronized
WAITING:當不滿足條件時,線程需要等待,如wait()方法和join()方法
TIMED_WAITING:需要等待一段時間,如sleep和帶時間參數的join()方法
後面會在狀态轉換一節詳述
TERMINATED 當線程代碼運作結束
join()函數屬于WAITING
sleep()函數屬于TIMED_WAITING
關于這兩種方法的特性可參看多線程基礎
3.線程的6種狀态示範
@Slf4j(topic = "c.Test5")
public class TestState {
public static void main(String[] args) {
//沒有調用線程1的start方法,是以屬于new這個狀态
Thread t1=new Thread("t1"){
@Override
public void run() {
log.debug("running...");
}
};
Thread t2=new Thread("t2"){
@Override
public void run() {
while(true){} //RUNNABLE(可能分了時間片,也可能陷入IO阻塞)
}
};
t2.start();
Thread t3=new Thread("t3"){
@Override
public void run() {
log.debug("running...");
}
};
//t3線程start完之後就結束了,是以最終進入了terminated
t3.start();
Thread t4=new Thread("t4"){
@Override
public void run() {
synchronized (TestState.class){
try {
//sleep的時間足夠長,主線程檢視線程狀态可以檢視到Time_Waiting
Thread.sleep(1000000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
};
t4.start();
Thread t5=new Thread("t5"){
@Override
public void run() {
try{
//等待包含死循環的t2運作結束,是以t5會一直等待,沒有time的叫Waiting
t2.join();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
};
t5.start();
Thread t6=new Thread("t6"){
@Override
public void run() {
//由于t4線程已經對TestState.class上鎖了,t6拿不到鎖,就會陷入到blocked狀态
synchronized (TestState.class){
try {
Thread.sleep(10000000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
};
t6.start();
Log.debug("t1 state {}",t1.getState());
Log.debug("t2 state {}",t2.getState());
Log.debug("t3 state {}",t3.getState());
Log.debug("t4 state {}",t4.getState());
Log.debug("t5 state {}",t5.getState());
Log.debug("t6 state {}",t6.getState());
}
}
運作結果:
c.TestState[t3]-running
c.TestState[main]-t1 state NEW
c.TestState[main]-t2 state RUNNABLE
c.TestState[main]-t3 state TERMINATED
c.TestState[main]-t4 state TIMED_WAITING
c.TestState[main]-t5 state WAITTING
c.TestState[main]-t6 state BLOCKED