Java并發編程:什么是線程優先級?
線程優先級是操作系統在調度線程時為每個線程分配的執行順序優先級。優先級較高的線程會先于優先級較低的線程執行。
在Java中,線程的優先級可以設置為1到10之間的值,默認的線程優先級是5。
源碼:
圖片
- MIN_PRIORITY:線程的最低優先級,值為1。
- NORM_PRIORITY:線程的默認優先級,值為5。
- MAX_PRIORITY:線程的最高優先級,值為10。
然而,并非所有操作系統都支持10個級別的優先級(例如,有些操作系統只支持3個級別:低、中、高)。
Java只是為操作系統提供了一個線程優先級的參考值。線程在操作系統中的最終優先級仍然由操作系統決定。
線程的執行順序最終由操作系統中的調度器決定,線程的優先級肯定是在線程被調用之前設置的。
一般來說,優先級較高的線程比優先級較低的線程有更高的機會被執行。我們可以使用Thread
類的setPriority()
方法來設置線程的優先級。
public class Demo {
public static void main(String[] args) {
Thread a = new Thread();
System.out.println("默認線程優先級: " + a.getPriority());
Thread b = new Thread();
b.setPriority(9);
System.out.println("設置線程優先級: " + b.getPriority());
}
}
輸出:
默認線程優先級: 5
設置線程優先級: 9
為什么不推薦使用線程優先級?
既然有1到10的級別來設置線程的優先級,你可能會問:我可以在業務代碼中使用這個方法來指定某些線程的執行順序嗎?
我的回答是:不行!
Java中的優先級并不可靠,在Java程序中設置的線程優先級只是對操作系統的一個建議,操作系統不一定會采納。實際的執行順序由操作系統的線程調度算法決定。
讓我們用代碼來驗證一下:
public class TestExecuteOrder {
staticclass MyRunnable implements Runnable {
@Override
public void run() {
System.out.printf("當前執行的線程是: %s, 優先級: %d%n",
Thread.currentThread().getName(),
Thread.currentThread().getPriority());
}
}
public static void main(String[] args) {
Thread t1 = new Thread(new MyRunnable());
t1.setPriority(1);
Thread t2 = new Thread(new MyRunnable());
t2.setPriority(5);
Thread t3 = new Thread(new MyRunnable());
t3.setPriority(10);
t3.start();
t2.start();
t1.start();
}
}
如果按順序執行,這個程序應該按照10、5、1的順序輸出。
但看看某個特定的輸出:
當前執行的線程是: Thread-1, 優先級: 5
當前執行的線程是: Thread-2, 優先級: 10
當前執行的線程是: Thread-0, 優先級: 1
優先級為5的線程實際上在優先級為10的線程之前輸出了結果,所以看起來這個優先級設置確實不可靠 。
線程優先級與線程組優先級的關系
在前一篇文章中,我們討論過線程必須存在于一個線程組中。那么,當線程的優先級與線程組的優先級不同時會發生什么呢?讓我們用以下代碼來驗證:
public class ThreadGroupOrder {
public static void main(String[] args) {
ThreadGroup myThreadGroup = new ThreadGroup("myThreadGroup");
myThreadGroup.setMaxPriority(6);
Thread myThread = new Thread(myThreadGroup, "myThread");
myThread.setPriority(8);
System.out.println("線程組優先級: " + myThreadGroup.getMaxPriority());
System.out.println("線程優先級: " + myThread.getPriority());
}
}
輸出:
線程組優先級: 6
線程優先級: 6
所以,如果線程的優先級高于它所在的線程組的優先級,那么該線程的優先級將失效,并被替換為線程組的最大優先級。