java中的runnable關鍵字用途 Runnable接口的3個實現技巧

runnable接口Thread類協同工作的核心機制是:將實現runnable接口的任務對象傳遞給thread類構造函數,再通過start()方法啟動線程。1. runnable接口定義任務邏輯,通過run()方法實現;2. thread類負責執行任務,需將runnable對象傳入其構造函數;3. 調用thread對象的start()方法啟動線程,觸發runnable的run()方法執行。例如:創建myrunnable類實現runnable接口并重寫run(),在main類中實例化myrunnable對象,并將其作為參數傳入thread構造函數,最后調用thread.start()啟動線程。

java中的runnable關鍵字用途 Runnable接口的3個實現技巧

Runnable 接口在 Java 中主要用于實現多線程,它允許你定義一個任務,然后讓一個線程去執行這個任務,而不需要繼承 Thread 類。這在需要繼承其他類的情況下尤其有用,因為 Java 不支持多重繼承

java中的runnable關鍵字用途 Runnable接口的3個實現技巧

Runnable 接口的核心作用就是解耦任務的定義和執行,你可以將任務邏輯封裝在 Runnable 實現類中,然后將這個 Runnable 對象傳遞給 Thread 對象來執行。

java中的runnable關鍵字用途 Runnable接口的3個實現技巧

實現 Runnable 接口,你可以更靈活地控制線程的創建和管理,避免了直接繼承 Thread 類帶來的局限性。

立即學習Java免費學習筆記(深入)”;

java中的runnable關鍵字用途 Runnable接口的3個實現技巧

Runnable 接口如何與Thread類協同工作?

Runnable 接口本身只是定義了一個 run() 方法,你需要將實現了 Runnable 接口的對象傳遞給 Thread 類的構造函數,然后調用 Thread 對象的 start() 方法來啟動線程。

public class MyRunnable implements Runnable {     @Override     public void run() {         System.out.println("線程正在執行...");     } }  public class Main {     public static void main(String[] args) {         MyRunnable myRunnable = new MyRunnable();         Thread thread = new Thread(myRunnable);         thread.start();     } }

在這個例子中,MyRunnable 類實現了 Runnable 接口,并重寫了 run() 方法。在 Main 類中,我們創建了一個 MyRunnable 對象,并將其傳遞給 Thread 類的構造函數。然后,我們調用 thread.start() 方法來啟動線程。

Runnable 接口的3個實現技巧

  1. 使用 Lambda 表達式簡化 Runnable 實現

Java 8 引入了 Lambda 表達式,可以更簡潔地實現 Runnable 接口。如果你的 Runnable 實現非常簡單,可以使用 Lambda 表達式來代替傳統的匿名內部類。

Thread thread = new Thread(() -> {     System.out.println("線程正在執行..."); }); thread.start();

Lambda 表達式讓代碼更簡潔易讀,特別是在處理簡單的任務時。

  1. 利用 ExecutorService 管理線程池

直接創建和管理線程可能會導致資源浪費和性能問題。使用 ExecutorService 可以更有效地管理線程池,它可以重用線程,避免頻繁創建和銷毀線程的開銷。

import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors;  public class Main {     public static void main(String[] args) {         ExecutorService executor = Executors.newFixedThreadPool(5); // 創建一個固定大小的線程池          for (int i = 0; i < 10; i++) {             int taskNumber = i;             executor.execute(() -> {                 System.out.println("線程 " + Thread.currentThread().getName() + " 正在執行任務 " + taskNumber);             });         }          executor.shutdown(); // 關閉線程池     } }

在這個例子中,我們創建了一個固定大小為 5 的線程池,然后提交了 10 個任務給線程池。ExecutorService 會自動分配線程來執行這些任務,并在任務完成后重用線程。

  1. 結合 Future 接口獲取線程執行結果

Runnable 接口的 run() 方法沒有返回值。如果需要獲取線程執行的結果,可以結合 Future 接口使用。Future 接口提供了 get() 方法,可以阻塞等待線程執行完成并獲取結果。

import java.util.concurrent.*;  public class Main {     public static void main(String[] args) throws ExecutionException, InterruptedException {         ExecutorService executor = Executors.newSingleThreadExecutor();          Callable<String> task = () -> {             Thread.sleep(1000); // 模擬耗時操作             return "線程執行完成";         };          Future<String> future = executor.submit(task);          System.out.println("等待線程執行結果...");         String result = future.get(); // 阻塞等待線程執行完成          System.out.println("線程執行結果:" + result);          executor.shutdown();     } }

在這個例子中,我們使用了 Callable 接口,它類似于 Runnable 接口,但 call() 方法可以返回一個值。我們使用 ExecutorService 提交 Callable 任務,并獲取 Future 對象。然后,我們調用 future.get() 方法來等待線程執行完成并獲取結果。

Runnable 和 Thread 的選擇:什么時候應該使用哪個?

如果你的類需要繼承其他類,那么只能選擇實現 Runnable 接口。如果你的類不需要繼承其他類,并且希望直接控制線程的行為,那么可以選擇繼承 Thread 類。但通常情況下,推薦使用 Runnable 接口,因為它更靈活,更符合面向對象的設計原則。

如何處理 Runnable 接口中的異常?

Runnable 接口的 run() 方法不能拋出受檢異常(checked exception)。如果 run() 方法中可能會拋出受檢異常,你需要使用 try-catch 塊來捕獲并處理這些異常。

public class MyRunnable implements Runnable {     @Override     public void run() {         try {             // 可能會拋出受檢異常的代碼             Thread.sleep(1000);         } catch (InterruptedException e) {             e.printStackTrace();         }     } }

如果 run() 方法中拋出了未受檢異常(unchecked exception),那么線程會終止,并且異常會傳播到調用線程的 uncaughtExceptionHandler 中。你可以設置 uncaughtExceptionHandler 來處理這些未受檢異常。

? 版權聲明
THE END
喜歡就支持一下吧
點贊5 分享