解讀線程池中submit()和execute()區(qū)別與聯(lián)系
關(guān)于線程池的繼承關(guān)系可參考:
在 Java 的線程池中,submit()和execute()都是用來向線程池提交任務(wù)的方法。區(qū)別在于任務(wù)類型支持、返回值和異常處理機(jī)制。
1、execute
1.1、定義
execute()是Executor接口(ExecutorService繼承自它)中定義的方法,只能提交Runnable任務(wù),沒有返回值不能獲取任務(wù)執(zhí)行結(jié)果,如果任務(wù)拋出異常,異常會(huì)由線程池的未捕獲異常處理器處理。
1.2、方法
execute(
Runnable command)
- 定義:來自Executor接口(ExecutorService繼承自它)。
- 參數(shù):僅接受Runnable類型的任務(wù)。
- 返回值:無返回值(void)。
代碼示例如下:
ExecutorService threadPool = Executors.newFixedThreadPool(2); threadPool.execute(()->{ System.out.println("hello execute"); });
1.3、異常處理
如果Runnable拋出未檢查異常(如RuntimeException),線程池會(huì)捕獲異常并打印堆棧信息,但調(diào)用者無法直接獲取異常。
? executor.execute(() -> { throw new RuntimeException("Error in execute()"); }); // 調(diào)用者無法捕獲此異常 ?
2、submit
2.1、介紹
submit() 是ExeCutorSevice 接口中定義的方法。
可以提交Runnable和Callable任務(wù),返回**Future**對象,可以用來獲取任務(wù)執(zhí)行結(jié)果或取消任務(wù)。
對于**Runnable**任務(wù),返回的**Future****在任務(wù)完成后會(huì)返回null,**異常會(huì)被捕獲并存儲(chǔ)在Future中,只有在調(diào)用Future.get()時(shí)才會(huì)拋出。
2.2、方法重載形式
<T> Future<T> submit(Callable<T> task); Future<?> submit(Runnable task); <T> Future<T> submit(Runnable task, T result);
參數(shù):
- 支持Runnable和Callable兩種任務(wù)類型。
- 如果是Runnable,可以通過第三個(gè)參數(shù)指定返回值(result)。
返回值:
- 返回Future對象,用于跟蹤任務(wù)狀態(tài)、獲取結(jié)果或取消任務(wù)。
1、Future<?> submit(Runnable task);
Future<?> submit = threadPool.submit(() -> { System.out.println("hello submit1"); }); try { submit.get(); } catch (Exception e) { e.printStackTrace(); }
2、<T> Future<T> submit(Runnable task, T result);
Future<String> submit1 = threadPool.submit(() -> { System.out.println("hello submit2"); }, "submit"); try { String object = (String) submit1.get(); System.out.println("object=="+object); } catch (Exception e) { e.printStackTrace(); }
3、<T> Future<T> submit(Callable<T> task);
Future<Integer> submit2 = threadPool.submit(() -> { return 1; }); try { Integer integer = submit2.get(); System.out.println("integer=="+integer); } catch (Exception e) { e.printStackTrace(); }
2.3、異常處理
異常會(huì)被封裝在ExecutionException中,通過Future.get()拋出,調(diào)用者可以顯式處理。
Future<?> future = executor.submit(() -> { throw new RuntimeException("Error in submit()"); }); try { future.get(); // 會(huì)拋出 ExecutionException } catch (ExecutionException e) { System.out.println("Caught exception: " + e.getCause().getMessage()); }
3、核心區(qū)別對比
心得
- 優(yōu)先使用submit():在大多數(shù)實(shí)際場景中,submit()提供了更強(qiáng)大的功能(如結(jié)果獲取、異常處理)。
- 關(guān)閉線程池:任務(wù)提交完成后,調(diào)用executor.shutdown()或executor.shutdownNow()釋放資源。
- 避免資源泄漏:確保線程池正確關(guān)閉,尤其是長期運(yùn)行的應(yīng)用程序。
通過合理選擇execute()和submit(),可以靈活控制任務(wù)的執(zhí)行和管理,滿足不同業(yè)務(wù)需求。
總結(jié)
以上為個(gè)人經(jīng)驗(yàn),希望能給大家一個(gè)參考,也希望大家多多支持腳本之家。
相關(guān)文章
java迭代器移除元素出現(xiàn)并發(fā)修改異常的原因及解決
這篇文章主要介紹了java迭代器移除元素出現(xiàn)并發(fā)修改異常的原因及解決,具有很好的參考價(jià)值,希望對大家有所幫助。一起跟隨小編過來看看吧2020-12-12Java數(shù)據(jù)庫連接池連接Oracle過程詳解
這篇文章主要介紹了Java數(shù)據(jù)庫連接池連接Oracle過程詳解,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下2020-09-09mybatis單筆批量保存實(shí)體數(shù)據(jù)的方法
這篇文章主要介紹了mybatis單筆批量保存實(shí)體數(shù)據(jù)的相關(guān)知識(shí),非常不錯(cuò),具有參考借鑒價(jià)值,需要的朋友可以參考下2018-01-01IDEA2020導(dǎo)入非maven項(xiàng)目并部署tomcat的方法
這篇文章主要介紹了IDEA 2020 導(dǎo)入非maven項(xiàng)目并部署tomcat的方法,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2020-07-07