3

Exceptionここでは、との違いに関する一般的な質問を数多く見てきましたThrowable。私は違いを知っており、より具体的な質問があります。

私は、ユーザーが提供するいくつかのコードをバインドして一緒に実行するライブラリを作成しています。ピースの 1 つが失敗すると、計算全体が破棄されます。リソースの使用をクリーンに保つために、ユーザーは、そのようなイベントが発生したときに実行されるファイナライザーを提供することもできます。パターンは次のようなものです。

try {
   // process ...
} catch (Exception ex) {
    runRegisteredFinalizers();
    throw ex;
}

私の質問は次のとおりです。上記のように sをインターセプトして再スローする必要がありますかException、それとも s もインターセプトする必要がありThrowableますか? 発生した場合Error、その可能性はありますか

  • JVM は回復しますか? (では、ファイナライザーを実行する意味はありますか?)
  • JVM は、実際に実行できる状態になりますか?

また、ファイナライザーを実行するときは、例外をキャッチして無視するので、登録されている他のファイナライザーが実行される可能性があります。たとえば、次のようになります。

  try {
      finalizer.run();
  }
  catch (Exception ex) {
    log.error("Exception in a finalizer", ex);
  }

繰り返しますが、s だけをインターセプトする必要がありますか?ExceptionまたはThrowables もインターセプトする必要がありますか? sを無視して再スローしないことErrorは、より問題があるようです。

4

2 に答える 2

1

何も想定できないユーザー提供のコードを扱っている場合は、スロー可能(どちらの場合も)をキャッチし、システム全体に影響を与えないリンケージエラーを検討する必要があります。実行中のコードは、NoSuchMethodErrorまたはNoClassDefFoundError

システム全体に影響を与えるエラーが発生した場合に諦めたい場合は、OOMEのようにVirtualMachineErrorを拡張するエラーをキャッチまたは再スローすることはできません。

于 2013-03-08T21:32:53.727 に答える
1

おそらく最も安全な方法は、Throwable (または Exception と Error を個別に) をキャッチし、キャッチされたものの参照を runRegisteredFinalizers() に渡して、ユーザーが気にする必要があるかどうかを判断する機会を与えることです。

ただし、キャッチできるエラーは、ツールキットに固有のもの (必ずしもユーザーのコードからではありません) か、ユーザーが説明しなかったもの (ユーザーがケース自体をトラップしたと仮定) のいずれかです。これらの場合、例外の種類は問題ではありません。

ただし、どちらの場合でも、ツールキットの性質と、エラーを見逃すことによる潜在的な影響に応じて、それをキャッチすることも理にかなっている場合があります。

于 2013-03-08T21:18:43.217 に答える