Java サブスレッドでの例外処理の一般的な方法の概要
以下のエディターは、Java サブスレッドでの例外処理メソッド (一般) に基づいた記事を提供します。編集者はこれがとても良いものだと思ったので、皆さんの参考として今から共有します。エディターを追って見てみましょう。通常のシングルスレッド プログラムでは、例外をキャッチするには try...catch...finally... コード ブロックのみが必要です。では、同時実行の状況では、たとえば、子スレッドが親スレッドで開始された場合、親スレッドで子スレッドからの例外をキャッチし、それに応じて処理するにはどうすればよいでしょうか?
よくある間違い とても簡単なことだと思う人もいるかもしれませんが、親スレッドが子スレッドを開始する場所を直接キャッチしてください。実際、これは間違っています。
原因分析 Runnable インターフェイスの run メソッドの完全なシグネチャを思い出してください。 throws ステートメントが識別されていないため、メソッドはチェック例外をスローしません。 RuntimeException などの未チェック例外については、JVM によって新規スレッドがスケジュールされて実行されるため、例外が発生しても親スレッドには通知されません。
public abstract void run()
Solutionそれでは、親スレッドで子スレッドからの例外をキャッチするにはどうすればよいでしょうか?筆者はよくある方法を3つ考え、みんなに共有しました。
方法 1: 子スレッドで try...catch... 最も簡単で効果的な方法は、例外が発生する可能性がある子スレッドのメソッドで try...catch を使用することです。 .. ステートメントがラップされています。サブスレッド コード:
public class ChildThread implements Runnable { public void run() { doSomething1(); try { // 可能发生异常的方法 exceptionMethod(); } catch (Exception e) { // 处理异常 System.out.println(String.format("handle exception in child thread. %s", e)); } doSomething2(); } }
方法 2: スレッドの例外ハンドラー UncaughtExceptionHandler を設定しますスレッドの例外ハンドラーを設定します。具体的なメソッドは次のとおりです。
(1) Thread.setUncaughtExceptionHandler は、現在のスレッドの例外ハンドラーを設定します。
(2) Thread.setDefaultUncaughtExceptionHandler は、現在のスレッドに例外ハンドラーがある場合、プログラム全体のデフォルトの例外ハンドラーを設定します。 (デフォルトは none) )、UncaughtExceptionHandler クラスが最初に使用されます。それ以外の場合、現在のスレッドが属するスレッド グループに例外ハンドラーがある場合は、スレッド グループの ExceptionHandler が使用されます。それ以外の場合は、グローバル デフォルトの DefaultUncaughtExceptionHandler が使用されます。何もない場合、子スレッドは終了します。
注: 子スレッドで例外が発生した場合、処理を引き継ぐクラスがない場合、子スレッドはログを残さずに直接終了します。したがって、何もしなければ、サブスレッドタスクが実行されず、ログプロンプトも表示されないという「奇妙な」現象が発生します。
現在のスレッドの例外ハンドラーを設定します:
public class ChildThread implements Runnable { private static ChildThreadExceptionHandler exceptionHandler; static { exceptionHandler = new ChildThreadExceptionHandler(); } public void run() { Thread.currentThread().setUncaughtExceptionHandler(exceptionHandler); System.out.println("do something 1"); exceptionMethod(); System.out.println("do something 2"); } public static class ChildThreadExceptionHandler implements Thread.UncaughtExceptionHandler { public void uncaughtException(Thread t, Throwable e) { System.out.println(String.format("handle exception in child thread. %s", e)); } } }
または、すべてのスレッドのデフォルトの例外ハンドラーを設定します
public class ChildThread implements Runnable { private static ChildThreadExceptionHandler exceptionHandler; static { exceptionHandler = new ChildThreadExceptionHandler(); Thread.setDefaultUncaughtExceptionHandler(exceptionHandler); } public void run() { System.out.println("do something 1"); exceptionMethod(); System.out.println("do something 2"); } private void exceptionMethod() { throw new RuntimeException("ChildThread exception"); } public static class ChildThreadExceptionHandler implements Thread.UncaughtExceptionHandler { public void uncaughtException(Thread t, Throwable e) { System.out.println(String.format("handle exception in child thread. %s", e)); } } }
コマンドライン出力: 子スレッドで 1
例外を処理します。 lang .RuntimeException: ChildThread例外
方法3、Futureのgetメソッドで例外をキャッチスレッドプールを使用して、戻り情報を取得できるメソッド、つまりExecutorService.submit(Callable)をサブミットします。 submit後にメソッドを取得できる スレッドの実行結果のFutureオブジェクトを子スレッドで例外が発生した場合、future.get()で戻り値を取得する際にExecutionException例外をキャッチすることで例外が発生したことを知ることができます。子スレッドで。
子スレッドのコード:
public class ChildThread implements Callable { public Object call() throws Exception { System.out.println("do something 1"); exceptionMethod(); System.out.println("do something 2"); return null; } private void exceptionMethod() { throw new RuntimeException("ChildThread1 exception"); } }
親スレッドのコード:
public class Main { public static void main(String[] args) { ExecutorService executorService = Executors.newFixedThreadPool(8); Future future = executorService.submit(new ChildThread()); try { future.get(); } catch (InterruptedException e) { System.out.println(String.format("handle exception in child thread. %s", e)); } catch (ExecutionException e) { System.out.println(String.format("handle exception in child thread. %s", e)); } finally { if (executorService != null) { executorService.shutdown(); } } } }
コマンドライン出力: 子スレッドで1
例外を処理します。java.util.concurrent.ExecutionException: java.lang.RuntimeException。 : ChildThread1 例外
概要上記は、よく使用される 3 つの Java 子スレッド例外処理メソッドです。実際、著者は特定のシナリオで他のいくつかの解決策も考えました。それらについてはまた別の機会に分析しますので、よろしくお願いします~
。以上がJava サブスレッドでの例外処理の一般的な方法の概要の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

ホットAIツール

Undresser.AI Undress
リアルなヌード写真を作成する AI 搭載アプリ

AI Clothes Remover
写真から衣服を削除するオンライン AI ツール。

Undress AI Tool
脱衣画像を無料で

Clothoff.io
AI衣類リムーバー

AI Hentai Generator
AIヘンタイを無料で生成します。

人気の記事

ホットツール

メモ帳++7.3.1
使いやすく無料のコードエディター

SublimeText3 中国語版
中国語版、とても使いやすい

ゼンドスタジオ 13.0.1
強力な PHP 統合開発環境

ドリームウィーバー CS6
ビジュアル Web 開発ツール

SublimeText3 Mac版
神レベルのコード編集ソフト(SublimeText3)

ホットトピック









Java の Weka へのガイド。ここでは、weka java の概要、使い方、プラットフォームの種類、利点について例を交えて説明します。

この記事では、Java Spring の面接で最もよく聞かれる質問とその詳細な回答をまとめました。面接を突破できるように。

Java 8は、Stream APIを導入し、データ収集を処理する強力で表現力のある方法を提供します。ただし、ストリームを使用する際の一般的な質問は次のとおりです。 従来のループにより、早期の中断やリターンが可能になりますが、StreamのForeachメソッドはこの方法を直接サポートしていません。この記事では、理由を説明し、ストリーム処理システムに早期終了を実装するための代替方法を調査します。 さらに読み取り:JavaストリームAPIの改善 ストリームを理解してください Foreachメソッドは、ストリーム内の各要素で1つの操作を実行する端末操作です。その設計意図はです

Java での日付までのタイムスタンプに関するガイド。ここでは、Java でタイムスタンプを日付に変換する方法とその概要について、例とともに説明します。

カプセルは3次元の幾何学的図形で、両端にシリンダーと半球で構成されています。カプセルの体積は、シリンダーの体積と両端に半球の体積を追加することで計算できます。このチュートリアルでは、さまざまな方法を使用して、Javaの特定のカプセルの体積を計算する方法について説明します。 カプセルボリュームフォーミュラ カプセルボリュームの式は次のとおりです。 カプセル体積=円筒形の体積2つの半球体積 で、 R:半球の半径。 H:シリンダーの高さ(半球を除く)。 例1 入力 RADIUS = 5ユニット 高さ= 10単位 出力 ボリューム= 1570.8立方ユニット 説明する 式を使用してボリュームを計算します。 ボリューム=π×R2×H(4

Spring Bootは、Java開発に革命をもたらす堅牢でスケーラブルな、生産対応のJavaアプリケーションの作成を簡素化します。 スプリングエコシステムに固有の「構成に関する慣習」アプローチは、手動のセットアップを最小化します。
