例外処理

Javaでは、プログラム実行中に発生するエラーや例外に対し適切な対応が取れるよう、try – catch – finallyブロックによる構造化例外処理が行えます。
例外処理の中では事前に定義された例外クラスを使って発生した例外を検出し、例外ごとに対応した対処を記述します
勿論、発生し得る例外全てに例外クラスが定義されているわけではないので、プログラムの処理に合わせ既存の例外クラスを継承して独自の例外クラスを定義することが可能です。

Javaにおける例外は、大きく2つに分かれます。

エラー(Error)
実行環境のトラブルなど、プログラムからは回復不可能なトラブルが発生したことを指します。
トラブルが発生した場合、JVMがErrorクラスまたは、そのサブクラスのインスタンスを生成しプログラムに適知します。
ただ、通知されたエラーはプログラムで対処できない事象なのでtry-catch したり、throws宣言する必要はありません。勿論、例外処理を記述することは可能で、検出されたエラーをユーザに知らせ対応をユーザに委ねることはできます。
例外(Exception)
プログラムが対処できる不具合(例外)です。
例外はさらに、検査例外と非検査例外に分かれます。
検査例外
例外処理を記述して正常な処理に復帰させることが可能な例外であり、プログラムで対処することが必須です。従って、コンパイラは例外処理の記述があるかどうかを確認し、必要な例外処理が存在しない場合はコンパイルエラーを出します。
対象はException及び、RuntimeExceptionを除くExceptionのサブクラスで、対処は検査例外が発生する可能性のある処理を、try-catchするか、throws宣言をしてメソッド呼び出し元に例外処理を移譲します。
非検査例外
プログラムでは対処が完全には行えないRuntimeExceptionとそのサブクラスの例外です。従って、try-catchなどの対処は必要なく、コンパイラは例外処理の記述あるかどうかを検査しません。
例外処理は必須ではありませんが、勿論try-catchして例外を検出し可能な範囲の対処を行い、正常終了させることは可能です。
全ての例外はThrowableクラスのサブクラスであり、各クラスの継承関係は、
Object
 ┃
Throwable
 ┣━Error
 ┗━Exception
    ┗━RuntimeException
となっています。

各例外の概要は以下の通りです。
Error
プログラム処理では回復出来ない不具合のため例外処理の記述は不要です。プログラム実行前にこのようなエラーが発生しないように実行環境を整えておく必要があります。
NoClassDefFoundError
JVMが実行対象のクラスファイルを発見できなかった
コンパイル時点で存在していたクラスが、見つからない
StackOverflowError
JVMが「再帰呼び出し」などで、スタック領域の不足を検出し、プログラムを強制終了
OutOfMemoryError
JVMがインスタンスを保存したり、クラスの定義情報を保存したりするヒープ領域が一杯になり、新しいオブジェクトを割り当てることができない
ExceptionInInitializerError
JVMがstaticイニシャライザを処理している間に例外が発生(NullPointerExceptionなど)したとき、例外の通達相手がいないのでErrorを発生させ、プログラムを強制終了
Exception
プログラム処理による回復が可能な不具合のため例外処理の記述が必須です。コンパイラーは例外処理の記述をチャックします。
ClassNotFoundException
クラスの文字列名を使用してforName、findSystemClass、loadClassメソッドでロードしようとしたが、指定された名前のクラスの定義が見つからなかった
IOException
入出力処理の失敗、または割り込みの発生による例外
FileNotFoundException
指定されたパス名で示されるファイルが開けなかった
SQLException
データベース操作時に発生した例外
RuntimeException
プログラム処理による完全な回復は不可能であり、例外処理の記述ではなく開発段階でロジックを精査し不具合が発生しないようにする必要があります。なお、コンパイラーは例外処理の記述をチャックしません。
ArithmeticException
ゼロ割等、不能演算が指示された
IllegalArgumentException
利用される側のオブジェクトが不正な引数を受取った
NumberFormatException
parselntメソッドが変換形式に合わない引数を受取った
例えば、Integerクラスのparselntメソッドに文字として英数字以外を渡す。
IndexOutOfBoundsException
配列や文字列、コレクションの範囲外アクセス
ArrayIndexOutOfBoundsException
配列の範囲外アクセス
public class Main01 {
	public static void main(String[] args) {
		String[] str = new String[1];
		for(String s :str) {
			System.out.println(s + " , " + str[1]);
		}
	}
}
>java Main01
Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: 1
        at Main01.main(Main01.java:5)

>
StringlndexOutOfBoundsException
文字列の範囲外アクセス
public class Main03 {
	public static void main(String[] args) {
		String str = "string";
		System.out.println(str.charAt(6));
	}
}
>java Main03
Exception in thread "main" java.lang.StringIndexOutOfBoundsException: String index out of range: 6
        at java.lang.String.charAt(Unknown Source)
        at Main03.main(Main03.java:4)

>
NullPointerException
オブジェクト参照がnullの状態で、インスタンスにアクセス
配列変数がnullなのに、配列のサイズを調べる
public class Main02 {
	public static void main(String[] args) {
		String[][] str = null;
		System.out.println(str.length);
	}
}
>java Main02
Exception in thread "main" java.lang.NullPointerException
        at Main02.main(Main02.java:4)

>
ClassCastException
継承関係や実現関係にない型に互換性のないクラスをキャストしようとした。
(コンパイル時には検出できず実行時に例外発生)
IlegalStateException
利用される側のオブジェクトが、まだ利用するための準備が終わっていない
カテゴリー: Java タグ: , , , , , パーマリンク