はじめに
Javaプログラムを書いていると、必ず遭遇するのが例外(エラー)です。特にEclipseなどのIDEで実行した際に出るスタックトレースは、エラーの原因を特定するための重要な手がかりですが、初心者にはちょっと難しいですよね。
この記事では、スタックトレースの構造を理解し、実際の例を使って読み解き方を解説し、エラーの特定から修正までの流れを体験してみます。
1, エラーが発生
まず、こんな簡単なJavaコードがあったとします。
package com.ittoybox.error;
public class Calc {
public int add(String a, String b) {
// 数値の文字列をintに変換して足し算する
return Integer.valueOf(a) + Integer.valueOf(b);
}
}
package com.ittoybox.error;
public class Main {
public static void main(String[] args) {
Calc calc = new Calc();
int result = calc.add("10", "b"); // ここで "b" は数値ではないためエラーになる
System.out.println(result);
}
}
このコードを実行すると、次のようなスタックトレースが出ます。
Exception in thread "main" java.lang.NumberFormatException: For input string: "b"
at java.lang.NumberFormatException.forInputString(NumberFormatException.java:65)
at java.lang.Integer.parseInt(Integer.java:580)
at java.lang.Integer.valueOf(Integer.java:766)
at com.ittoybox.error.Calc.add(Calc.java:7)
at com.ittoybox.error.Main.main(Main.java:8)
2. スタックトレースの構造を理解しよう
スタックトレースは2つのパートから成り立っています。
① エラー情報
Exception in thread "main" java.lang.NumberFormatException: For input string: "b"
これは
1. どのような例外が発生したか(NumberFormatException)
2. 例外メッセージ("b" は数値に変換できない)
を示します。
補足
Javaにはよくある例外がたくさんあります。例外名 → 意味
1. NullPointerException → nullオブジェクトにアクセスしたときに発生
2. ArrayIndexOutOfBoundsException → 配列の範囲外のインデックスにアクセスしたときに発生
3. ClassNotFoundException → クラスが見つからないときに発生
4. IllegalArgumentException → メソッドの引数が無効なときに発生
エラー内容はJavaの公式ドキュメント(JavaDoc)を参照すれば、何が起きているのか予測できるのでぜひそちらも活用してみてください。
② スタックトレース情報(呼び出し履歴)
スタック(積み上げた)トレース(追跡情報)なので、一番下が最初に呼ばれたメソッドで、一番上がエラーが発生した箇所です。
つまり、下から上へ辿るイメージです。
今回の例だと、
com.ittoybox.error.Main.main(Main.java:8)
↓
com.ittoybox.error.Calc.add(Calc.java:7)
↓
java.lang.Integer.valueOf(Integer.java:766)
↓
java.lang.Integer.parseInt(Integer.java:580)
↓
java.lang.NumberFormatException発生
となり、
①Main.javaの8行目でCalc.addメソッドが呼ばれて、
②Calc.javaの7行目でInteger.valueOfが呼ばれ、
③Integer.parseIntでエラーが起きたこと
がわかります。
③ エラーの特定方法
スタックトレースを見たら、
-
自分やチームで作ったクラス・メソッド(今回だとcom.ittoybox.error.CalcやMain)を重点的に見る
-
それ以外はライブラリやJavaの標準クラスなので、エラーの原因ではない可能性が高い
今回の例はCalc.addの7行目付近に問題がありそうです。
④ エラーの修正
今回のエラーは、Integer.valueOfに渡した文字列"b"が数値変換できないため起こったようです。
そのため、次のように入力値をチェックしたり、例外処理を追加すると良いでしょう。
public int add(String a, String b) {
try {
return Integer.valueOf(a) + Integer.valueOf(b);
} catch (NumberFormatException e) {
System.err.println("数値変換に失敗しました: " + e.getMessage());
return 0; // エラー時のデフォルト値
}
}
まとめ
スタックトレースはエラー原因を特定する最重要情報なので
-
まずエラー情報(例外の種類・メッセージ)を確認する
-
次に呼び出し履歴(スタックトレース)を下から上へたどる
-
自作コードのどこでエラーが起きたかを見極める
-
必要に応じて例外処理や入力値チェックを入れて修正する
これでEclipseのエラーと戦う基礎が身につきます。ぜひ実際の開発に役立ててみてくださいね^^