Revised: Feb./15th/2003: Since: Jan./27th/2002
ここでは単純な例外処理のサンプルを示します。
ArrayIndexOutOfBoudsException
java.lang.Object | +--java.lang.Throwable | +--java.lang.Exception | +--java.lang.RuntimeException | +--java.lang.IndexOutOfBoundsException | +--java.lang.ArrayIndexOutOfBoundsException
不正なインデックスを使って配列がアクセスされたことを示します。
class TestExcep1 { public static void main(String[] args) { System.out.println("実行開始。"); try { System.out.println(args[0]); System.out.println("tryブロック終了"); } catch (ArrayIndexOutOfBoundsException e) { System.out.println("例外:" + e); System.out.println("引数を一つ入力してください。"); } System.out.println("実行終了。"); } }
C:\java>javac TestExcep1.java C:\java>java TestExcep1 実行開始。 例外:java.lang.ArrayIndexOutOfBoundsException 引数を一つ入力してください。 実行終了。
引数の配列の個数が正しくないために起こった例外です。この場合は、ロジックで容易に回避できます:
if (args.length != 1) { System.out.println("引数を一つ入力してください。"); return; }
配列 args[]
の要素数が1でない場合に true
となり、ブロック内が実行されます。
NumberFormatException
java.lang.Object | +--java.lang.Throwable | +--java.lang.Exception | +--java.lang.RuntimeException | +--java.lang.IllegalArgumentException | +--java.lang.NumberFormatException
文字列を数値型に変換しようとしたとき、文字列の形式が正しくない場合にスローされます。
class TestExcep2 { public static void main(String[] args) { System.out.println("実行開始。"); try { int i; i=Integer.parseInt(args[0]); //引数がないか、整数に直せなかったら例外がスローされる System.out.println(i*100); System.out.println("tryブロック終了"); } catch (ArrayIndexOutOfBoundsException e) { System.out.println("例外:" + e); System.out.println("引数を一つ入力してください。"); } catch (NumberFormatException e) { System.out.println("例外:" + e); System.out.println("引数を整数で入力してください。"); } System.out.println("実行終了。"); } }
C:\java>javac TestExcep2.java C:\java>java TestExcep2 実行開始。 例外:java.lang.ArrayIndexOutOfBoundsException 引数を一つ入力してください。 実行終了。 C:\java>java TestExcep2 3.14 実行開始。 例外:java.lang.NumberFormatException: 3.14 引数を整数で入力してください。 実行終了。
ArithmeticException
java.lang.Object | +--java.lang.Throwable | +--java.lang.Exception | +--java.lang.RuntimeException | +--java.lang.ArithmeticException
算術計算で例外的条件が発生した場合にスローされます。たとえば、整数を「ゼロで除算」するとこのクラスのインスタンスがスローされます。
class TestExcep2 { public static void main(String[] args) { System.out.println("実行開始。"); try{ int i, j=100; System.out.println("j: " + j); i=Integer.parseInt(args[0]); System.out.println("j/i: " + j/i); //0で割ると例外がスローされる System.out.println("tryブロック終了"); } catch (ArrayIndexOutOfBoundsException e) { System.out.println("例外:" + e); System.out.println("引数を一つ入力してください。"); } catch (NumberFormatException e) { System.out.println("例外:" + e); System.out.println("引数を整数で入力してください。"); } catch (ArithmeticException e) { System.out.println("例外:" + e); System.out.println("引数を0以外の整数で入力してください。"); } System.out.println("実行終了。"); } }
引数が与えられない場合は、最初の catch ブロックにつかまります。引数は与えられるけど、整数に変換できない場合は、二番目の catch ブロックにつかまります。引数が与えられて整数に変換できるけど、それがゼロであった場合は、ゼロ割りになって三番目の catch ブロックにつかまります。
C:\java>javac TestExcep3.java C:\java>java TestExcep3 0 実行開始。 j: 100 例外:java.lang.ArithmeticException: / by zero 引数を0以外の整数で入力してください。 実行終了。 C:\java>java TestExcep3 -5 実行開始。 j: 100 j/i: -20 tryブロック終了 実行終了。
Exception
発生する例外を全てキャッチしたい場合は、 Exception
型でキャッチすることができます。
全ての例外クラスは Exception
クラスをスーパークラスに持ちます。したがって、全ての例外クラスを Exception
型として catch できるのです。
class TestExcep4 {
public static void main(String[] args) {
String str=null;
try {
System.out.println(str.length());
} catch (Exception e) {
System.out.println("例外:" + e);
}
}
}
このサンプルでは、 null 値が代入された文字列型オブジェクトに length()
メソッドを要求しています。文字列が代入されていれば、文字の個数を返しますが、 null 値の場合は、例外 NullPointException
が発生します。
C:\java>javac TestExcep4.java C:\java>java TestExcep4 例外:java.lang.NullPointerException
このサンプルでは、 NullPointerException
という例外が発生していますが、 Exception
型の例外としてきちんと拾われています。全ての例外は Exception
から派生しているので、自動型変換されてキャッチされるのです。
Exception 型は全ての例外オブジェクトと代入互換なので、最後に記述する必要があります。Exception 型を最初に記述してしまうと、全ての例外オブジェクトがそこでキャッチされてしまうので、後続の catch ブロックには絶対に制御が移らないのです。先ほどの ArithmaticException のキャッチの例を挙げると、 Exception は最後に記述すべきです。
class TestExcep2 {
public static void main(String[] args) {
System.out.println("実行開始。");
try{
int i, j=100;
System.out.println("j: " + j);
i=Integer.parseInt(args[0]);
System.out.println("j/i: " + j/i);
//0で割ると例外がスローされる
System.out.println("tryブロック終了");
} catch (ArrayIndexOutOfBoundsException e) {
System.out.println("例外:" + e);
System.out.println("引数を一つ入力してください。");
} catch (NumberFormatException e) {
System.out.println("例外:" + e);
System.out.println("引数を整数で入力してください。");
} catch (ArithmeticException e) {
System.out.println("例外:" + e);
System.out.println("引数を0以外の整数で入力してください。");
} catch (Exception e) {
System.out.println("なんらかの例外が発生しました。");
e.printStackTrace();
}
System.out.println("実行終了。");
}
}