《Java併發編程的藝術》第一章--上下文切換、避免死鎖、資源限制的挑戰

主要是學習的簡單記錄,用來加深印象。第一章主要仍是理論多,做者簡單的描述。web

1.1.1上下文切換算法

也就是CPU切換調度線程。不論是單核仍是多核,CPU會給每一個線程分配CPU時間片,時間片是CPU分配給線程的時間,由於時間片很是短,因此CPU經過不停地切換線程執行,讓咱們感受多個線程是同時執行,時間片通常是幾十毫秒(ms)。當一個線程執行完一個時間片後CPU會切換到其餘線程,此時前一個線程會暫停,保存對應的任務狀態,等再次切回來的時候會加載這個任務的狀態繼續執行,而不是從新執行。從保存到再加載的過程就是一次上下文的切換。數據庫

1.1.2如何減小上下文切換編程

並非線程越多程序執行就越快,線程多的話致使上下文切換也頻繁,那麼須要考慮減小上下文切換。減小上下文切換的方法有無鎖併發編程、CAS算法、使用最少線程和使用協程。服務器

  • 無鎖併發編程。多線程競爭鎖時,會引發上下文切換,因此多線程處理數據時,能夠用一些辦法來避免使用鎖,如將數據的ID按照Hash算法取模分段,不一樣的線程處理不一樣段的數據。
  • CAS算法。Java的Atomic包使用CAS算法來更新數據,而不須要加鎖。
  • 使用最少線程。避免建立不須要的線程,好比任務不多,可是建立了不少線程來處理,這樣會形成大量線程都處於等待狀態。
  • 協程:在單線程裏實現多任務的調度,並在單線程裏維持多個任務間的切換。

1.2 如何避免死鎖多線程

避免死鎖的幾個常見方法。併發

  • 避免一個線程同時獲取多個鎖
  • 避免一個線程在鎖內同時佔用多個資源,儘可能保證每一個鎖只佔用一個資源。
  • 嘗試使用定時鎖,使用lock.tryLock(timeout)來替代使用內部鎖機制。
  • 對於數據庫鎖,加鎖和解鎖必須在一個數據庫鏈接裏,不然會出現解鎖失敗的狀況。

1.3資源的限制socket

(1)什麼是資源限制工具

資源限制是指在進行併發編程時,程序的執行速度受限於計算機硬件資源軟件資源oop

例如,服務器的帶寬只有2Mb/s,某個資源的下載速度是1Mb/s每秒,系統啓動10個線程下載資

源,下載速度不會變成10Mb/s,因此在進行併發編程時,要考慮這些資源的限制。硬件資源限

制有帶寬的上傳/下載速度、硬盤讀寫速度和CPU的處理速度。軟件資源限制有數據庫的鏈接

數和socket鏈接數等。

(2)資源限制引起的問題

在併發編程中,將代碼執行速度加快的原則是將代碼中串行執行的部分變成併發執行,

可是若是將某段串行的代碼併發執行,由於受限於資源,仍然在串行執行,這時候程序不只不

會加快執行,反而會更慢,由於增長了上下文切換和資源調度的時間。例如,以前看到一段程

序使用多線程在辦公網併發地下載和處理數據時,致使CPU利用率達到100%,幾個小時都不

能運行完成任務,後來修改爲單線程,一個小時就執行完成了。

(3)如何解決資源限制的問題

對於硬件資源限制,能夠考慮使用集羣並行執行程序。既然單機的資源有限制,那麼就讓

程序在多機上運行。好比使用ODPS、Hadoop或者本身搭建服務器集羣,不一樣的機器處理不一樣

的數據。能夠經過「數據ID%機器數」,計算獲得一個機器編號,而後由對應編號的機器處理這

筆數據。

對於軟件資源限制,能夠考慮使用資源池將資源複用。好比使用鏈接池將數據庫和Socket

鏈接複用,或者在調用對方webservice接口獲取數據時,只創建一個鏈接。

(4)在資源限制狀況下進行併發編程

如何在資源限制的狀況下,讓程序執行得更快呢?方法就是,根據不一樣的資源限制調整

程序的併發度,好比下載文件程序依賴於兩個資源——帶寬和硬盤讀寫速度。有數據庫操做

時,涉及數據庫鏈接數,若是SQL語句執行很是快,而線程的數量比數據庫鏈接數大不少,則

某些線程會被阻塞,等待數據庫鏈接。

1.4 總結

本章介紹了在進行併發編程時,你們可能會遇到的幾個挑戰,並給出了一些解決建議。有

的併發程序寫得不嚴謹,在併發下若是出現問題,定位起來會比較耗時和棘手。因此,對於

Java開發工程師而言,筆者強烈建議多使用JDK併發包提供的併發容器和工具類來解決併發

問題,由於這些類都已經經過了充分的測試和優化,都可解決了本章提到的幾個挑戰。

相關文章
相關標籤/搜索