併發(1)中斷線程,線程的狀態,線程屬性。

一 ,中斷線程   

   獲取當前線程: System.out.println(Thread.currentThread());    

   結果爲:Thread[main,5,main]   指的是當前線程的字符串表示形式。Thread[main,5,main]爲主線程的表示方式,中括號裏的第一個值爲當前主線程的名字,第二個爲線程級別,第三個爲線程組。Thread[Thread-0,5,main]Thread-0爲另一個啓動的線程,級別爲5,屬於線程組main

  當線程的 run 方法執行方法體中最後一條語句後, 並經由執行 return 語句返冋時,或者出現了在方法中沒有捕獲的異常時,線程將終止。 在 Java 的早期版本中, 還有一個 stop 方法, 其他線程可以調用它終止線程。但是, 這個方法現在已經被棄用。

       沒有可以強制線程終止的方法。然而,interrupt 方法可以用來請求終止線程。

      當對一個線程調用 interrupt 方法時,線程的中斷狀的 boolean 標誌。每個線程都應該不時地檢査這個標誌, 要想弄清中斷狀態是否被置位,首先調用靜態的Thread.currentThread 方法獲得當前線程, 然後調用 islnterrupted 方法:

while (!Thread.currentThread().islnterrupted() && more work to do)
{
do more work
}

• void interrupts()

向線程發送中斷請求。線程的中斷狀態調用阻塞,那麼,InterruptedException 

•static boolean interrupted()

測試當前線程(即正在執行這一命令的線程)是否被中斷。注意,這是一個靜態方法。這一調用會產生副作用—它將當前線程的中斷狀態重置爲 false.

• boolean islnterrupted()

測試線程是否被終止。不像靜態的中斷方法,這一調用不改變線程的中斷狀態。

•static Thread currentThread()

返回代表當前執行線程的 Thread 

二 ,線程的狀態

線程可以有如下 6 種狀態:

•New (新創建)

•Runnable (可運行)

•Blocked (被阻塞)

•Waiting (等待)

•Timed waiting (計時等待)

•Terminated (被終止)

新創建線程

      當用 new 操作符創建一個新線程時,如 newThread(r), 該線程還沒有開始運行。這意味着它的狀態是 new。當一個線程處於新創建狀態時,程序還沒有開始運行線程中的代碼。在線程運行之前還有一些基礎工作要做。

可運行線程

       一旦調用 start 方法,線程處於 runnable 狀態。一個可運行的線桿可能正在運行也可能沒有運行, 這取決於操作系統給線程提供運行的時間。(Java 的規範說明沒有將它作爲一個單獨狀態。一個正在運行中的線程仍然處於可運行狀態。)

       一旦一個線程開始運行,它不必始終保持運行。事實上,運行中的線程被中斷,目的是爲了讓其他線程獲得運行機會。線程調的細節依賴於操作系統提供的服務。搶佔式調度系統給每一個可運行線程一個時間片來執行任務。當時間片用完,操作系統剝奪該線程的運行權, 並給另一個線程運行機會。

記住,在任何給定時刻,二個可運行的線程可能正在運行也可能沒有運行(這就是爲什麼將這個狀態稱爲可運行而不是運行。)

被阻塞線程和等待線程

       當線程處於被阻塞或等待狀態時,它暫時不活動。它不運行任何代碼且消耗最少的資源。直到線程調度器重新激活它。細節取決於它是怎樣達到非活動狀態的。

      (1)當一個線程試圖獲取一個內部的對象鎖(而不是 javiutiUoncurrent 庫中的鎖,) 而該鎖被其他線程持有, 則該線程進人阻塞狀態

      (2)當線程等待另一個線程通知調度器一個條件時,它自己進入等待狀態。

       ( 3 ) 有幾個方法有一個超時參數。調用它們導致線程進人計時等待( timed waiting ) 狀態。這一狀態將一直保持到超時期或者接收到適當的通知。帶有超時參數的方法有Thread.sleep 和 Object.wait、Thread.join、 Lock,tryLock 以及 Condition.await 的計時版。

       當一個線程被阻塞或等待時(或終止時,) 另一個線程被調度爲運行狀態。當一個線程被重新激活(例如, 因爲超時期滿或成功地獲得了一個鎖,) 調度器檢查它是否具有比當前運行線程更高的優先級。如果是這樣,調度器從當前運行線程中挑選一個, 剝奪其運行權,選擇一個新的線程運行。

被終止的線程

線程因如下兩個原因之一而被終止:
   •因爲 run 方法正常退出而自然死亡。

   •因爲一個沒有捕獲的異常終止了 run()方法而意外。

3 .線程屬性

(1)優先級

       在 Java 程序設計語言中,每一個線程有一個優先級。默認情況下, 一+線程繼承它的父線程的優先級。可以用 setPriority 方法提高或降低任何一個線程的優先級。可以將優先級設置爲在 MIN_PRIORITY (在 Thread 類中定義爲 1 ) 與 MAX_PRIORITY (義爲 10 ) 之間的任何值。NORM_PRIORITY 被定義爲 5。

       每當線程調度器有機會選擇新線程時, 它首先選擇具有較高優先級的線程。但是,線程優先級是高度依賴於系統的。當虛擬機依賴於宿主機平臺的線程實現機制時, Java 線程的優先級被映射到宿主機平臺的優先級上, 優先級個數也許更多,也許更少。例如,Windows 有 7 個優先級別。一些 Java 優先級將映射到相同的操作系統優先級在Oracle 爲 Linux 提供的 Java 虛擬機中,線程的優先級被忽略一所有線程具有相同的優

     如果確實要使用優先級, 應該避免初學者常犯的一個錯誤。如果有幾個高優先級的線程沒有進入非活動狀態, 低優先級的線程可能永遠也不能執行。每當調度器決定運行一個新線程時,首先會在具有高優先級的線程中進行選擇, 儘管這樣會使低優先的線程完全餓死。

(2)守護線程

       可以通過調用t.setDaemon(true);

      將線程轉換爲守護線程(daemon thread。) 這樣一個線程沒有什麼神奇。守護線程的唯一用途是爲其他線程提供服務。計時線程就是一個例子,它定時地發送“ 計時器嘀嗒” 信號給其他線程或清空過時的高速緩存項的線程。當只剩下守護線程時, 虛擬機就退出了,由於如果只剩下守護線程, 就沒必要繼續運行程序了。 守護線程應該永遠不去訪問固有資源, 如文件、 數據庫,因爲它會在任何時候甚至在一個操作的中間發生中斷。

 (3) 未捕獲異常處理器

        線程的 run方法不能拋出任何受查異常, 但是,非受査異常會導致線程終止。在這種情況下,線程就死亡了。

        但是,不需要任何 catch子句來處理可以被傳播的異常。相反,就在線程死亡之前, 異常被傳遞到一個用於未捕獲異常的處理器。

        該處理器必須屬於一個實現 Thread.UncaughtExceptionHandler 接口的類。這個接口只有—個方法。

void uncaughtException(Thread t, Throwable e)

    可以用 setUncaughtExceptionHandler 方法爲任何線程安裝一個處理器。也可以用 Thread類的靜態方法 setDefaultUncaughtExceptionHandler 爲所有線程安裝一個默認的處理器。替換處理器可以使用日誌 API 發送未捕獲異常的報告到日誌文件。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章