Code Fix

上級

raw type とワイルドカードの使い分け

型引数を省くと型安全が失われます。List<Object>とList<?>の違いも整理します。

エラーメッセージの読み方

Main.java:8: error: incompatible types: Object cannot be converted to String
Main.java
ファイル名
8
行番号 — javacが異常に気づいた位置。原因の行とは限りません
error
種別 — コンパイルエラー。実行まで到達しません
incompatible types: Object cannot be converted to String
内容 — javacが期待していたもの、または見つけられなかったもの

このエラーが出る典型パターン

パターン1

 1  import java.util.ArrayList;
 2  import java.util.List;
 3  
 4  public class Main {
 5      public static void main(String[] args) {
 6          List         list = new ArrayList<>();
                    ^
 7          list.add("a");
 8          String s = list.get(0);
 9          System.out.println(s);
10      }
11  }
Main.java:8: error: incompatible types: Object cannot be converted to String

型引数を省くと生の型になり、要素はObjectとして扱われます。取り出すたびにキャストが必要になります。

直し方: (空)<String> にします。

この問題を解いてみる →

広告
広告スロット(未設定)

パターン2

 1  import java.util.List;
 2  
 3  public class Main {
 4      static void show(List<Object> list) {
                                 ^
 5          for (Object o : list) System.out.println(o);
 6      }
 7      public static void main(String[] args) {
 8          List<Integer> nums = List.of(1, 2, 3);
 9          show(nums);
10      }
11  }
Main.java:9: error: incompatible types: List<Integer> cannot be converted to List<Object>

List<Integer>はList<Object>の部分型ではありません。何でも受けるにはワイルドカード ? を使います。

直し方: Object? にします。

この問題を解いてみる →

パターン3

 1  public class Main {
 2      static <T> T first(java.util.ArrayList <T> list) {
                                     ^
 3          return list.get(0);
 4      }
 5      public static void main(String[] args) {
 6          System.out.println(first(java.util.List.of("a")));
 7      }
 8  }
Main.java:6: error: method first in class Main cannot be applied to given types; required: ArrayList<T> found: List<String> reason: cannot infer type-variable(s) T

引数は最も広い型で受けるのが原則です。ArrayListで受けるとListしか持たない呼び出し側が渡せません。

直し方: java.util.ArrayListjava.util.List にします。

この問題を解いてみる →

よくある誤解

警告だけでコンパイルは通ります。通ってしまうからこそ、本番で ClassCastException として現れます。

まとめ

raw type とワイルドカードの使い分けは上級でつまずきやすい項目です。上の3パターンを実際に手で直すと、エラーメッセージのどこを読めばよいかが掴めます。

演習をはじめる

関連するエラー

広告
広告スロット(未設定)