多線程學習和補充:接口之間的關係等等

[TOC]html

1、概念理解

一、進程和線程java

  • 進程是操做系統級別的概念:
    • 一個系統中能夠有多個進程;
  • 線程是進程中劃分的概念:
    • 一個進程中能夠劃分多個線程;

二、處理器:個數和多核:編程

  • 一個處理器在某一個時間點上永遠都只能是一個線程!即便這個處理器是多核的。
    • 多核能夠提高線程的執行效率,但多核不能同時運行多個線程。
  • 多個處理器才能同時運行多個線程。

2、使用多線程:Runnable 接口和 Thread 類

2.一、Runnable 接口

如上:api

  • Runnable 是一個功能型函數(JAVA 8 新特性)。
  • 它是一個接口;
  • 它只定義了一個 run() 方法。public abstract void run();

官方文檔:Runnable (Java Platform SE 8 )多線程

2.二、Thread 類

注意:Thread 類實現了 Runnable 接口。併發

具體類的學習挺複雜挺多的,後續再看和分析。函數

2.3 使用多線程

2.3.1 方式一:實現 Runnable 接口

使用步驟工具

  1. 一個類 A,實現 Runnable 接口。該類須要重寫 run()方法,即爲線程的實現內容;
  2. 建立類 A 的對象 A-1;
  3. 將對象 A-1 做爲 Thread 類的構造函數的入參,獲得一個 Thread 類對象 T-1;
  4. 執行 T-1對象的 start() 方法,啓動線程;
  5. 結束

2.3.2 方式二:繼承 Thread 類

使用步驟post

  1. 一個類 T, 繼承 Thread 類。該類須要重寫 run()方法,即爲線程的實現內容;
  2. 建立類 T 的對象 T-1;
  3. 執行 T-1對象的 start() 方法,啓動線程;
  4. 結束

2.3.3 兩種步驟的區別:

繼承 Thread 類比實現 Runnable 接口簡潔了一步,在於學習

  • 繼承 Thread 類會直接將 run() 方法的實現賦予到對象中。
  • 可是實現 Runnable 接口須要經過對應的構造函數將 run() 方法的實現賦予到對象中。

具體的代碼實現能夠見原文:Java 多線程學習(一)Java 多線程入門 - 掘金

3、各接口之間的關係

各接口之間的關係:

  • Callable 接口 和 Runnable 接口
    • Callable 接口只有一個 call() 方法,這是一個泛型接口,call () 函數返回的類型就是傳遞進來的 V 類型。
    • Runnable 接口只有一個 run() 方法。
    • 二者無明顯關係;
  • Callable 接口 和 Future接口
    • 如上圖,二者也無明顯關係
  • Executor 和 Runnable接口
    • 如上圖,Executor 只和Runnable 有關係。execute() 方法的入參是 Runnable 。
    • Executor 和 Callable 以及 Future並沒有明顯關係;
  • ExecutorService 接口
    • 這是一個很神奇的接口
      • 首先它繼承自 Executor :意味着和 Runnable 接口有關係
    • 它經過submit()方法把 Runnable 與Callable 和 Future結合了起來
      • Runnable 與Callable做爲方法入參,Future做爲返回結果;
    • 它經過invokeAll()方法把 Callable 和 Future結合了起來,並且都是List的那種;
    • invokeAny()方法暫時找不到用途。

4、其餘關係:

4.1 FutureTask 和 Future 的關係

關係以下圖,FutureTask 實現了 Future 接口和 Runnable 接口。其餘就是FutureTask 本身的方法,本身的實現邏輯。 注意:FutureTask 是 Future 接口的一個惟一實現類。

咱們重點看下FutureTask 的調用邏輯:(其餘複雜實現暫時無論。)

  1. 執行線程而且獲得返回結果
    • run() 方法負責線程調用,內部實際調用的是 Callable 接口。
      • 獲得調用結果後調用本身的 set() 方法
      • set() 方法:將線程結果設置爲本身的一個屬性:outcome
  2. 取出線程結果:
    • get() 方法內部實際調用本身的 report() 方法,並返回 report() 方法的返回結果;
    • report() 方法:從自身的 outcome 屬性取值並返回。

上述就是對於 FutureTask 的具使用邏輯

4.2 Executors 和 ScheduledThreadPoolExecutor、ThreadPoolExecutor、Executor

4.2.1 Executors 和其餘的關係 :

  • 從依賴關係上康,Executors和其餘接口和類沒什麼關係。

Executors 究竟是作什麼的?

Executors是一個工具類,相似StringUtils等的封裝。用於提供一些經常使用的線程池。通常網上都是說提供四種線程池:

  • newCachedThreadPool:(實現是:ThreadPoolExecutor)
  • newFixedThreadPool:(實現是:ThreadPoolExecutor)
  • newScheduledThreadPool:(實現是:ScheduledThreadPoolExecutor)
  • newSingleThreadExecutor:(實現是:ThreadPoolExecutor)

但實際上,Executors 的方法不止這些,還有不少其餘方法。不知道爲何網上這樣說。 能夠看到,底層實現幾乎都是ThreadPoolExecutor。那麼爲何不直接使用ThreadPoolExecutor呢?由於 java doc 中不提倡直接用。

4.2.2 其餘:ScheduledThreadPoolExecutor、ThreadPoolExecutor、Executor之間的關係:

  • 首先區分接口和實現類:
    • 接口:Executor、ExecutorService、ScheduledExecutorService
    • 實現類:AbstractExecutorService、ThreadPoolExecutor、ScheduledThreadPoolExecutor
  • 而後對實現類再作區分
    • AbstractExecutorService 是線程池對象的抽象類(抽象類不能實例化)。
    • ThreadPoolExecutor、ScheduledThreadPoolExecutor能夠看做是 AbstractExecutorService 的子類。

5、參考:

  1. Java 多線程學習(一)Java 多線程入門 - 掘金 注:開始部分對於線程、進程和處理器的概念說明很棒。
  2. Future 解析與使用 - 林老師帶你學編程 - CSDN 博客 Callable 與 Runnable的關係說的很好,還有Future 和 Callable 的關係,還有ExecutorService 的關係
  3. Java Executors 和 ThreadPoolExecutor 線程池 - xlxxcc 的專欄 - CSDN 博客 注:說明了 Executors 和 ThreadPoolExecutor 線程池的關係。
  4. Java 併發編程:線程池的使用 - Matrix 海子 - 博客園 注:ThreadPoolExecutor 詳解。
相關文章
相關標籤/搜索