「ああ、いるね。ずっと探してたんだ。」

"なんかあったの?"

「いえ、でもまだ勉強中です。」

「わかりました。聞いています。」

「例外についてさらにいくつかお話ししたいと思います。」

「Java 7 では、try-catch構造は複数の catchブロックの追加によってわずかに拡張されました。次の例を見てください。」

Java 5
try
{
  …
}
 catch (IOException ex)
{
 logger.log(ex);
 throw ex;
}
 catch (SQLException ex)
{
 logger.log(ex);
 throw ex;
}
Java 7
try
{
  …
}
 catch (IOException | SQLException ex)
{
 logger.log(ex);
 throw ex;
}

「それでは、OR 演算子 ('|' はバイナリ OR) で区切って複数の例外を記述できますか?」

「そうだね。便利じゃない?」

「うーん。でも、catch ブロック内の例外オブジェクトの型はどうなるのでしょうか?」

「結局のところ、IOException には独自のメソッドがあり、SQLException には独自のメソッドがあります。」

「例外の型は、共通の祖先クラスの型になります。」

「ああ。つまり、おそらくExeptionRuntimeExceptionになるでしょう。それなら単純に catch(Exception e) と書けばいいのでは?」

「エラーを個別に処理する場合、一部のエラーをログに書き込み、他のエラーを再スローし、他の方法で他のエラーを処理するなど、エラーをグループ化すると便利な場合があります。」

「言い換えれば、このスキームは、異なるエラーを処理するための重複した catch ブロックの問題を解決すると認識されています。」

「ああ、分かった。ありがとう、エリー」

「それだけではありません。finally ブロックについてもう少し詳しくお話したいと思います。」

「おそらくすでにご存知かと思いますが、このブロックは常に実行されます。」

「そして、私がいつもと言っているのは、絶対に常にという意味です。」

"例えば:"

finally を使用した例
try
{
 return 1;
}
 finally
{
 return 0;
}

「ここでは、 tryブロックに戻りがあり、finallyブロックに戻りがあります。したがって、このメソッドの戻り値は数値 0 になります。」

finallyブロックは、何が起こっても実行されます。そして、そのreturnステートメントは、他の戻り値を独自の値で上書きします。」

"そうか。"

"ただし、メソッドは値を返すことも、例外をスローすることもできます。 "

「したがって、try ブロックで値が返されても、finallyブロックで例外がスローされた場合、結果は例外になります。

「 tryブロックで例外がスローされたが、 finallyブロックに return ステートメントがある場合はどうなるでしょうか?」

「そうすると、メソッドが正しく動作したかのように、return ステートメントの値が返されます。

結果
try
{
 return 1;
}
 finally
{
 return 0;
}
0
try
{
 return 1;
}
 finally
{
 throw new RuntimeException();
}
ランタイム例外
try
{
 throw new RuntimeException();
}
 finally
{
 return 0;
}
0
try
{
 throw new RuntimeException();
}
 finally
{
 throw new IOException();
}
IO例外

「finally メソッドが実行されない唯一の理由は、System.exit();メソッドの呼び出しによってプログラムが即時に終了することです。」

try
{
 System.exit(0);
 return 1;
}
 finally
{
 return 0;
}

"そうか。"

「これらのトピックはすべて、通常、面接で聞かれるので、理解し、覚えておくとよいでしょう。」