日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 编程语言 > java >内容正文

java

Java线程详解(7)-线程的调度

發(fā)布時(shí)間:2025/3/21 java 17 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Java线程详解(7)-线程的调度 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

Java線程:線程的調(diào)度-休眠

? ? ? ? Java線程調(diào)度是Java多線程的核心,只有良好的調(diào)度,才能充分發(fā)揮系統(tǒng)的性能,提高程序的執(zhí)行效率。

????????這里要明確的一點(diǎn),不管程序員怎么編寫調(diào)度,只能最大限度的影響線程執(zhí)行的次序,而不能做到精準(zhǔn)控制。

????????線程休眠的目的是使線程讓出CPU的最簡(jiǎn)單的做法之一,線程休眠時(shí)候,會(huì)將CPU資源交給其他線程,以便能輪換執(zhí)行,當(dāng)休眠一定時(shí)間后,線程會(huì)蘇醒,進(jìn)入準(zhǔn)備狀態(tài)等待執(zhí)行。

????????線程休眠的方法是Thread.sleep(long millis)和Thread.sleep(long millis, int nanos),均為靜態(tài)方法,那調(diào)用sleep休眠的哪個(gè)線程呢?簡(jiǎn)單說,哪個(gè)線程調(diào)用sleep,就休眠哪個(gè)線程。

/**?*?Java線程:線程的調(diào)度-休眠?*/?? public?class?TestSleep?{??public?static?void?main(String[]?args)?{??Thread?t1=new?MyThread1();??Thread?t2=new?Thread(new?MyRunnable());??t1.start();??t2.start();??}?? }?? class?MyThread1?extends?Thread{??@Override??public?void?run()?{??for(int?i=0;i<3;i++){??System.out.println("線程1第"+i+"次執(zhí)行!");??try?{??Thread.sleep(50);??}?catch?(InterruptedException?e)?{??e.printStackTrace();??}??}??}???? }?? class?MyRunnable?implements?Runnable{??@Override??public?void?run()?{???????for(int?i=0;i<3;i++){??System.out.println("線程2第"+i+"次執(zhí)行!");??try?{??Thread.sleep(50);??}?catch?(InterruptedException?e)?{??e.printStackTrace();??}??}??}???? }?

?
????????執(zhí)行結(jié)果:

線程1第0次執(zhí)行!?? 線程2第0次執(zhí)行!?? 線程2第1次執(zhí)行!?? 線程1第1次執(zhí)行!?? 線程2第2次執(zhí)行!?? 線程1第2次執(zhí)行!??


????????從上面的結(jié)果輸出可以看出,無法精準(zhǔn)保證線程執(zhí)行次序。

?

Java線程:線程的調(diào)度-優(yōu)先級(jí)

? ? ? ? 與線程休眠類似,線程的優(yōu)先級(jí)仍然無法保障線程的執(zhí)行次序。只不過,優(yōu)先級(jí)高的線程獲取CPU資源的概率較大,優(yōu)先級(jí)低的并非沒機(jī)會(huì)執(zhí)行。

????????線程的優(yōu)先級(jí)用1-10之間的整數(shù)表示,數(shù)值越大優(yōu)先級(jí)越高,默認(rèn)的優(yōu)先級(jí)為5。

????????在一個(gè)線程中開啟另外一個(gè)新線程,則新開線程稱為該線程的子線程,子線程初始優(yōu)先級(jí)與父線程相同。

/**?*?Java線程:線程的調(diào)度-優(yōu)先級(jí)?*/?? public?class?TestPriority?{??public?static?void?main(String[]?args)?{??Thread?t1=new?MyThread1();??Thread?t2=new?Thread(new?MyRunnable());??t1.setPriority(10);??t2.setPriority(1);??t1.start();??t2.start();??}?? }?? class?MyThread1?extends?Thread{??@Override??public?void?run()?{??for(int?i=0;i<10;i++){??System.out.println("線程1第"+i+"次執(zhí)行!");??try?{??Thread.sleep(100);??}?catch?(InterruptedException?e)?{??e.printStackTrace();??}??}??}???? }?? class?MyRunnable?implements?Runnable{??@Override??public?void?run()?{???????for(int?i=0;i<10;i++){??System.out.println("線程2第"+i+"次執(zhí)行!");??try?{??Thread.sleep(100);??}?catch?(InterruptedException?e)?{??e.printStackTrace();??}??}??}???? }??


????????執(zhí)行結(jié)果:

線程1第0次執(zhí)行!?? 線程1第1次執(zhí)行!?? 線程1第2次執(zhí)行!?? 線程2第0次執(zhí)行!?? 線程1第3次執(zhí)行!?? 線程2第1次執(zhí)行!?? 線程1第4次執(zhí)行!?? 線程2第2次執(zhí)行!?? 線程1第5次執(zhí)行!?? 線程2第3次執(zhí)行!?? 線程1第6次執(zhí)行!?? 線程2第4次執(zhí)行!?? 線程1第7次執(zhí)行!?? 線程2第5次執(zhí)行!?? 線程1第8次執(zhí)行!?? 線程2第6次執(zhí)行!?? 線程1第9次執(zhí)行!?? 線程2第7次執(zhí)行!?? 線程2第8次執(zhí)行!?? 線程2第9次執(zhí)行!??


Java線程:線程的調(diào)度-讓步

? ? ? ? 線程的讓步含義就是使當(dāng)前運(yùn)行著線程讓出CPU資源,但是讓給誰(shuí)不知道,僅僅是讓出,線程狀態(tài)回到可運(yùn)行狀態(tài)。

????????線程的讓步使用Thread.yield()方法,yield()為靜態(tài)方法,功能是暫停當(dāng)前正在執(zhí)行的線程對(duì)象,并執(zhí)行其他線程。

/**?*?Java線程:線程的調(diào)度-讓步?*/?? public?class?Test?{??public?static?void?main(String[]?args)?{??Thread?t1=new?MyThread1();??Thread?t2=new?Thread(new?MyRunnable());??t1.start();??t2.start();??}?? }?? class?MyThread1?extends?Thread{??@Override??public?void?run()?{??for(int?i=0;i<10;i++){??System.out.println("線程1第"+i+"次執(zhí)行!");??????????}??}???? }?? class?MyRunnable?implements?Runnable{??@Override??public?void?run()?{???????for(int?i=0;i<10;i++){??System.out.println("線程2第"+i+"次執(zhí)行!");??Thread.yield();??}??}???? }??


????????執(zhí)行結(jié)果:

線程2第0次執(zhí)行!?? 線程1第0次執(zhí)行!?? 線程1第1次執(zhí)行!?? 線程1第2次執(zhí)行!?? 線程1第3次執(zhí)行!?? 線程1第4次執(zhí)行!?? 線程1第5次執(zhí)行!?? 線程1第6次執(zhí)行!?? 線程1第7次執(zhí)行!?? 線程1第8次執(zhí)行!?? 線程1第9次執(zhí)行!?? 線程2第1次執(zhí)行!?? 線程2第2次執(zhí)行!?? 線程2第3次執(zhí)行!?? 線程2第4次執(zhí)行!?? 線程2第5次執(zhí)行!?? 線程2第6次執(zhí)行!?? 線程2第7次執(zhí)行!?? 線程2第8次執(zhí)行!?? 線程2第9次執(zhí)行!

??
Java線程:線程的調(diào)度-合并


????????線程的合并的含義就是將幾個(gè)并行線程的線程合并為一個(gè)單線程執(zhí)行,應(yīng)用場(chǎng)景是當(dāng)一個(gè)線程必須等待另一個(gè)線程執(zhí)行完畢才能執(zhí)行時(shí)可以使用join方法。

????????join為非靜態(tài)方法,定義如下:

void?join()——等待該線程終止。????? void?join(longmillis)——等待該線程終止的時(shí)間最長(zhǎng)為?millis毫秒。????? void?join(longmillis,int?nanos)——等待該線程終止的時(shí)間最長(zhǎng)為?millis毫秒?+?nanos?納秒。??

?

/**?*?Java線程:線程的調(diào)度-合并?*/?? public?class?Test?{??public?static?void?main(String[]?args)?{??Thread?t1=new?MyThread1();???????t1.start();??for?(int?i?=?0;?i?<?20;?i++)?{??System.out.println("主線程第"?+?i?+"次執(zhí)行!");??if?(i>2)?{??try?{??///t1線程合并到主線程中,主線程停止執(zhí)行過程,轉(zhuǎn)而執(zhí)行t1線程,直到t1執(zhí)行完畢后繼續(xù)。??t1.join();??}?catch?(InterruptedException?e)?{??e.printStackTrace();??}??}??}??}?? }?? class?MyThread1?extends?Thread{??@Override??public?void?run()?{??for(int?i=0;i<10;i++){??System.out.println("線程1第"+i+"次執(zhí)行!");??????????}??}???? }??


????????執(zhí)行結(jié)果:

主線程第0次執(zhí)行!?? 主線程第1次執(zhí)行!?? 主線程第2次執(zhí)行!?? 主線程第3次執(zhí)行!?? 線程1第0次執(zhí)行!?? 線程1第1次執(zhí)行!?? 線程1第2次執(zhí)行!?? 線程1第3次執(zhí)行!?? 線程1第4次執(zhí)行!?? 線程1第5次執(zhí)行!?? 線程1第6次執(zhí)行!?? 線程1第7次執(zhí)行!?? 線程1第8次執(zhí)行!?? 線程1第9次執(zhí)行!?? 主線程第4次執(zhí)行!?? 主線程第5次執(zhí)行!?? 主線程第6次執(zhí)行!?? 主線程第7次執(zhí)行!?? 主線程第8次執(zhí)行!?? 主線程第9次執(zhí)行!?? 主線程第10次執(zhí)行!?? 主線程第11次執(zhí)行!?? 主線程第12次執(zhí)行!?? 主線程第13次執(zhí)行!?? 主線程第14次執(zhí)行!?? 主線程第15次執(zhí)行!?? 主線程第16次執(zhí)行!?? 主線程第17次執(zhí)行!?? 主線程第18次執(zhí)行!?? 主線程第19次執(zhí)行!??


Java線程:線程的調(diào)度-守護(hù)線程

? ? ? ? 守護(hù)線程與普通線程寫法上基本么啥區(qū)別,調(diào)用線程對(duì)象的方法setDaemon(true),則可以將其設(shè)置為守護(hù)線程。

????????守護(hù)線程使用的情況較少,但并非無用,舉例來說,JVM的垃圾回收、內(nèi)存管理等線程都是守護(hù)線程。還有就是在做數(shù)據(jù)庫(kù)應(yīng)用時(shí)候,使用的數(shù)據(jù)庫(kù)連接池,連接池本身也包含著很多后臺(tái)線程,監(jiān)控連接個(gè)數(shù)、超時(shí)時(shí)間、狀態(tài)等等。

????????setDaemon方法的詳細(xì)說明:

public?final?void?setDaemon(boolean?on)將該線程標(biāo)記為守護(hù)線程或用戶線程。當(dāng)正在運(yùn)行的線程都是守護(hù)線程時(shí),Java虛擬機(jī)退出。??


????????該方法必須在啟動(dòng)線程前調(diào)用。
????????該方法首先調(diào)用該線程的 checkAccess方法,且不帶任何參數(shù)。這可能拋出 SecurityException(在當(dāng)前線程中)。
??????????參數(shù):on - 如果為true,則將該線程標(biāo)記為守護(hù)線程。
??????????拋出:
????????IllegalThreadStateException- 如果該線程處于活動(dòng)狀態(tài)。
????????SecurityException- 如果當(dāng)前線程無法修改該線程。
????????另請(qǐng)參見:
????????isDaemon(),checkAccess()

/**?*?Java線程:線程的調(diào)度-守護(hù)線程?*/?? public?class?Test?{??public?static?void?main(String[]?args)?{??Thread?t1=new?MyCommon();??Thread?t2=new?Thread(new?MyDaemon());??t2.setDaemon(true);//設(shè)置為守護(hù)線程??t2.start();??t1.start();????????}?? }?? class?MyCommon?extends?Thread{??@Override??public?void?run()?{??for(int?i=0;i<5;i++){??System.out.println("線程1第"+i+"次執(zhí)行!");??try?{??Thread.sleep(7);??}?catch?(InterruptedException?e)?{??e.printStackTrace();??}??}??}???? }?? class?MyDaemon?implements?Runnable{??@Override??public?void?run()?{??for?(long?i?=?0;?i?<?9999999L;?i++)?{??System.out.println("后臺(tái)線程第"?+?i?+"次執(zhí)行!");??try?{??Thread.sleep(7);??}?catch?(InterruptedException?e)?{??e.printStackTrace();??}??}??}???? }??


????????執(zhí)行結(jié)果:

線程1第0次執(zhí)行!?? 后臺(tái)線程第0次執(zhí)行!?? 后臺(tái)線程第1次執(zhí)行!?? 線程1第1次執(zhí)行!?? 后臺(tái)線程第2次執(zhí)行!?? 線程1第2次執(zhí)行!?? 后臺(tái)線程第3次執(zhí)行!?? 線程1第3次執(zhí)行!?? 后臺(tái)線程第4次執(zhí)行!?? 線程1第4次執(zhí)行!?? 后臺(tái)線程第5次執(zhí)行!?? 后臺(tái)線程第6次執(zhí)行!?? 后臺(tái)線程第7次執(zhí)行!?? 后臺(tái)線程第8次執(zhí)行!?? 后臺(tái)線程第9次執(zhí)行!?? 后臺(tái)線程第10次執(zhí)行!??


????????從上面的執(zhí)行結(jié)果可以看出:

????????前臺(tái)線程是保證執(zhí)行完畢的,后臺(tái)線程還沒有執(zhí)行完畢就退出了。

????????實(shí)際上:JRE判斷程序是否執(zhí)行結(jié)束的標(biāo)準(zhǔn)是所有的前臺(tái)執(zhí)線程行完畢了,而不管后臺(tái)線程的狀態(tài),因此,在使用后臺(tái)縣城時(shí)候一定要注意這個(gè)問題。
?

總結(jié)

以上是生活随笔為你收集整理的Java线程详解(7)-线程的调度的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。