1. 程式人生 > >Java第八周學習總結

Java第八周學習總結

允許 空間 線索 執行過程 優先 學習內容 沒有 sleep方法 isa

第12章 Java多線程機制

一、學習內容

12.1進程與進程

程序是一段靜態的代碼,進程是程序的一次動態執行過程,這個過程也是進程本身從產生、發展至消亡的過程。

12.2Java中的線程

1、Java的多線程機制

Java語言的一大特性點就是內置對多線程的支持。

多線程是指一個應用程序中同時存在幾個執行本,按幾條不同的執行線索共同工作的情況。

計算機在任何給定的時刻只能執行線程中的一個。Java虛擬機快速地把控制從一個線程切換到另一個線程,這些線程被輪流執行,使得每個線程都有機會使用CPU資源。

2、主線程(main線程)

主線程(main線程)負責執行main方法。

如果main方法中沒有創建其他的線程,那麽當main方法執行完最後一個語句,即main方法返回時,JVM就會結束Java應用程序。如果main方法中又創建了其他線程,那麽JVM就要在主線程和其他線程之間輪流切換,保證,每個線程都有機會使用CPU,main方法即使執行完最後的語句(主線程結束),JVM也不會結束Java應用程序,JVM一直要等到Java應用程序都結束之後,才結束Java應用程序。

3、線程的狀態和生命周期

Java語言使用Thread類及其子類的對象來表示線程。

新建的線程在一個完整的生命周期中通常要經歷以下4個狀態:

新建:一個Thread類或其子類的對象被聲明並創建,已經有了相應的內存空間和其他資源。

運行:JVM將CPU使用權切換給該線程時,此線程就可以脫離創建它的主線程獨立開始自己的生命周期了。
如果線程是Thread的子類創建的,該類中的run()方法就立刻執行,且程序必須在子類中重寫父類的run()方法。
在線程沒有結束run()方法之前,不要讓線程再調用start()方法,否則將發生IllegalThreadStateException異常。

4、線程調度與優先級

每個Java線程的優先級都在常數1和10之間,即Thread.MIN_PRIORITY 和Thread.MAX_PRIORITY之間。如果沒有明確地設置線程的優先級別,,每個線程的優先級都為常數5,即Thread.NORM_PRIORITY。

可以通過setPriority(int grade)方法調整優先級, getPriority 方法返回線程的優先級。

當線程使用CPU資源的時間到時後,即使線程沒有完成自己的全部操作,JVM也會中斷當前線程的執行,把CPU的使用權切換給下一個排隊等待的線程,當前線程將等待CPU資源的下一次輪回,然後從中斷處繼續執行。

12.3Thread類與線程的創建

  • 使用Thread的子類

在編寫Thread類的子類時,需要重寫父類的run()方法。

優點:可以在子類中增加新的成員變量,實現城具有某種屬性,也可以在子類中新增加方法,使線程具有某種功能。

Java不支持多繼承,Thread類的子類不能再擴展其他的類。

  • 使用Thread類。

用Thread類直接創建線程對象:Thread(Runnable target),該構造方法中的參數是一個Runnable類型的接口。
在創建線程對象時必須向構造方法的參數傳遞一個實現Runnable接口類的實例,該實例對象稱作所創線程的目標對象,當線程調用start()方法後,一旦輪到它來享用CPU資源,目標對象就會自動調用接口中的run()方法(接口回調)

對於使用同一目標對象的線程,目標對象的成員變量自然就是這些線程共享的數據單元,使用Runnable接口比使用Thread的子類更具有靈活性。

  • 目標對象與線程的關系

目標對象和線程完全解耦:目標對象經常需要通過獲得線程的名字(因為無法獲得線程對象的引用)以便確定被JVM正在執行的線程是哪個。

目標對象組合線程(弱耦合):目標對象可以組合線程,目標對象類組合線程對象時,目標對象可以通過獲得線程對象的引用。

  • 關於run方法啟動的次數

對於具有相同目標對象的線程,當其中一個線程享用CPU資源時,目標對象自動調用接口中的run方法,這時,run方法中的局部變量被分配內存空間,當輪到另一個線程享用CPU資源時,目標對象會再次調用接口中的run方法,run()方法中的局部變量會再次分配內存空間。即run()方法已經啟動運行了兩次,分別運行在不同的線程中

12.4線程的常用方法

start() : 線程調用該方法將啟動線程,使之從新建狀態進入就緒隊列排隊,一旦輪到它來享用CPU資源時,就可以脫離創建它的線程獨立開始自己的生命周期了。

run(): Thread類的run()方法與Runnable接口中的run()方法的功能和作用相同,都用來定義線程對象被調度之後所執行的操作,都是系統自動調用而用戶程序不得引用的方法。

sleep(int millsecond): 優先級高的線程可以在它的run()方法中調用sleep方法來使自己放棄CPU資源,休眠一段時間。

isAlive(): 線程處於“新建”狀態時,線程調用isAlive()方法返回false。在線程的run()方法結束之前,即沒有進入死亡狀態之前,線程調用isAlive()方法返回true。

currentThread():
該方法是Thread類中的類方法,可以用類名調用,該方法返回當前正在使用CPU資源的線程。

12.5線程同步

多個線程調用synchronized方法必須遵守同步機制。

在處理線程同步時,要做的第一件事就是要把修改數據的方法用關鍵字synchronized來修飾。

所謂線程同步就是若幹個線程都需要使用一個synchronized修飾的方法。

線程同步機制:當一個線程A使用synchronized方法時,其他線程想使用這個synchronized方法時就必須等待,直到線程A使用完該synchronized方法。

12.6協調同步的線程

wait()方法可以中斷方法的執行,使本線程等待,暫時讓出CPU的使用權,並允許其它線程使用這個同步方法。

notifyAll()方法通知所有的由於使用這個同步方法而處於等待的線程結束等待。曾中斷的線程就會從剛才的中斷處繼續執行這個同步方法,並遵循“先中斷先繼續”的原則。

notify()方法只是通知處於等待中的線程的某一個結束等待。

wait()、notify()、notifyAll()都是Object類中的final方法,被所有的類繼承且不允許重寫得方法。不可以在非同步方法中使用wait()、notify()、notifyAll()。

二、代碼截圖

技術分享圖片

三、碼雲鏈接:

https://gitee.com/BESTI-IS-JAVA-2018/20165213zqh

Java第八周學習總結