例外とは何か
皆さんは例外というものをどのようにとらえているでしょうか。初心者であれば極力お目に掛かりたくないし、避けて通りたいものかもしれません。それは「例外=エラー=悪」という単純な思い込みがあるからではないでしょうか。
しかしJavaの世界において例外を無視することはできません。そこで今回は言語仕様を元に例外というものがどのように定義されているかをみていくことにしましょう。例外の言語仕様は、「11 Exceptions(例外)」にまとめられています。
その冒頭では、例外とは何かを説明しています。
When a program violates the semantic constraints of the Java programming language, the Java virtual machine signals this error to the program as an exception.
(訳:プログラムが、プログラミング言語Javaにおけるセマンティクス上の制約に違反した場合、Java仮想マシンはこのエラーをプログラムに例外として通知する)。
セマンティクスとは何とも難しい表現ですが、これはプログラマがプログラムに込める意図と考えるとわかりやすいでしょう。その意図に反する場合、Javaではエラーをエラーのまま伝達するのではなく、エラーとは別のもの(ここでは「例外オブジェクト」と呼ぶ)にラッピングした形で伝達します。エラーがエラーそのものであるのに対して、例外はエラーの種類ごとに整理されたエラー情報を格納した器といえます。例外はエラーの別名ではなく、Javaの1つの機能に他なりません。
若干回りくどい説明をしましたが、言語仕様を読むとその背景がみえてきます。
Some programming languages and their implementations react to such errors by peremptorily terminating the program; other programming languages allow an implementation to react in an arbitrary or unpredictable way. Neither of these approaches is compatible with the design goals of the Java platform: to provide portability and robustness.
(訳:ある種のプログラミング言語やその実装では、プログラムの強制終了によってこういったエラーに対応していたり、またその他のプログラミング言語では、不定の結果や予測できない結果となることを実装に対して許しているものもある。こういったアプローチは、どちらもポータビリティと堅牢さを提供するというJavaプラットフォームの設計目標とは合致していない)。
つまり、他のプログラミング言語の反省点がJava言語の仕様策定に影響を与えているのです。言語仕様にはこのような背景も記載されているので興味深いですね。
さてJavaでは呼び出し元に異常を知らせるときは例外をスロー(throw)しますが、このことについてもなぜスローする必要があるのかを言語仕様では語っています。
Explicit use of throw statements provides an alternative to the old-fashioned style of handling error conditions by returning funny values, such as the integer value -1 where a negative value would not normally be expected. Experience shows that too often such funny values are ignored or not checked for by callers, leading to programs that are not robust, exhibit undesirable behavior, or both.
(訳:明示的なthrow文を使用することによって、従来では通常の場合には負の値が返されないはずの場所から整数値-1のような特異な値を返すことによって行われていた、旧式のエラー・ハンドリング手法に代わる手段が提供される。従来手法による特異な値が、無視されたり、呼び出し側でチェックされないことに起因するプログラムの堅牢性の低下、予期せぬ振る舞い、またその双方があまりにも数多く引き起こされることは経験が示す通りである)。
ここでも旧来の反省点を基に例外というものが考えられたことがおわかりでしょう。
例外の制御方法は、言語仕様により規定されています(図参照)。図に登場する例外オブジェクトとはnull型やプリミティブ型で、これらをスローすることはできません。つまり例外というオブジェクトを使用してエラー処理をコントロールしているのです。まさに例外こそオブジェクト指向的といえるでしょう。
次に、例外クラスについて理解していきましょう。 次のページ