リフレクションによるクラスの調査
実行時に Class オブジェクトを取得し、フィールド、メソッド、コンストラクター、アノテーションを調査します。
「リフレクションによるクラスの調査」はCoddyKit上の無料Java Academyレッスンです。 これはレッスン1/4です。 下記で完全なレッスンを無料で読むことができます。その後、ブラウザ内の組み込みコードエディタと24時間対応のAIチューターでハンズオン演習できます。 これはJava Academy学習パスの一部であり、ウェブとCoddyKitアプリ全体で進捗が同期されます。 Java Academyコースには全4レッスンが含まれています。
リフレクションとは
リフレクションを使用すると、Java プログラムは実行時に自身の構造を検査・操作できます。コンパイル時に把握していなくても、クラス名、フィールド、メソッド、コンストラクター、アノテーションを読み取れます。
Class オブジェクトの取得
クラスリテラル、getClass()、または Class.forName()を使用して、Class<?>オブジェクトを取得します。
Class<String> c1 = String.class; // literal
Class<?> c2 = "hello".getClass(); // from instance
Class<?> c3 = Class.forName("java.util.ArrayList"); // by nameクラスメタデータの検査
Classオブジェクトから、クラス名、パッケージ、スーパークラス、実装されたインターフェースを取得します。
Class<?> c = ArrayList.class;
System.out.println(c.getName()); // java.util.ArrayList
System.out.println(c.getSimpleName()); // ArrayList
System.out.println(c.getSuperclass()); // class java.util.AbstractList
for (Class<?> iface : c.getInterfaces()) System.out.println(iface.getName());宣言されたフィールドの一覧表示
getDeclaredFields()は、クラスで宣言されたすべてのフィールド(private を含む)を返します。getFields()は、継承されたものを含む public フィールドのみを返します。
for (Field f : User.class.getDeclaredFields()) {
System.out.printf("%-10s %s%n", f.getType().getSimpleName(), f.getName());
}メソッドの一覧表示
getDeclaredMethods()は、アクセス修飾子に関係なくすべてのメソッドを一覧表示します。継承されたものを含む public メソッドには getMethods()を使用します。
for (Method m : String.class.getDeclaredMethods()) {
System.out.println(m.getName() + " -> " + m.getReturnType().getSimpleName());
}メソッドパラメーターの検査
パラメーターの型、名前(-parametersコンパイラフラグが必要)、アノテーションを取得します。
Method m = UserService.class.getDeclaredMethod("findById", Long.class);
for (Parameter p : m.getParameters()) {
System.out.println(p.getType().getSimpleName() + " " + p.getName());
}コンストラクターの一覧表示
コンストラクターもメソッドと同じように検査できます。getDeclaredConstructors()には、シングルトンやビルダーで使用される private コンストラクターも含まれます。
for (Constructor<?> c : User.class.getDeclaredConstructors()) {
System.out.println(Arrays.toString(c.getParameterTypes()));
}アノテーションの読み取り
クラス、メソッド、フィールドに付与されたアノテーションを取得します。isAnnotationPresentで存在を確認し、getAnnotationで値を取得します。
@RestController
@RequestMapping("/users")
public class UserController {}
// Inspection:
RequestMapping rm = UserController.class.getAnnotation(RequestMapping.class);
if (rm != null) System.out.println("Path: " + Arrays.toString(rm.value()));修飾子の確認
フィールド、メソッド、クラスの修飾子に対して Modifier.isPublic()、isStatic()、isFinal()などを使用し、可視性で絞り込みます。
for (Field f : User.class.getDeclaredFields()) {
int mod = f.getModifiers();
if (Modifier.isPrivate(mod)) System.out.println("private: " + f.getName());
}isAssignableFrom と instanceof による確認
Class.isAssignableFrom()を使用すると、プログラムから型の互換性を確認できます。実行時にのみ判明するクラスオブジェクトを使って、instanceofと同等の確認を行えます。
Class<?> parent = Collection.class;
Class<?> child = ArrayList.class;
System.out.println(parent.isAssignableFrom(child)); // true
System.out.println(child.isAssignableFrom(parent)); // falseパフォーマンス上の注意点
単純なフィールドやメソッドへのアクセスでは、リフレクションは直接コードより 10~50 倍遅くなります。Fieldと Methodオブジェクトをキャッシュし、setAccessible(true)は一度だけ呼び出して再利用してください。
private static final Field NAME_FIELD;
static {
try { NAME_FIELD = User.class.getDeclaredField("name"); NAME_FIELD.setAccessible(true); }
catch (NoSuchFieldException e) { throw new RuntimeException(e); }
}理解度チェック
継承されたフィールドを除き、クラスの private フィールドを返すメソッドはどれですか?
まとめ
クラスリテラルまたは forName()で Classを取得します。すべてのアクセス修飾子を対象に検査するには getDeclaredFields/Methods/Constructorsを使用します。getAnnotationでアノテーションを読み取ります。パフォーマンスのために、リフレクションで扱うオブジェクトをキャッシュします。
よくある質問
「リフレクションによるクラスの調査」レッスンは無料ですか?
はい。「リフレクションによるクラスの調査」の完全なテキストはこのウェブで無料で読めます。インタラクティブに演習し(組み込みコードエディタと24時間対応のAIチューター)、Java Academyコースの残りをアンロックするには、CoddyKit PROにアップグレードしてください。 Java Academyコースには全4レッスンが含まれています。
「リフレクションによるクラスの調査」で何を学びますか?
実行時に Class オブジェクトを取得し、フィールド、メソッド、コンストラクター、アノテーションを調査します。 ブラウザで直接実行するハンズオンコードでJava Academyを演習し、24時間対応のAIチューターがレッスンを進める中での質問に答えます。
Java Academyを始めるのに経験は必要ですか?
事前経験は必要ありません。CoddyKitのJava Academyは初級者から上級者向けに構成されているため、ここから始めるか最初から始めて、自分のペースで進むことができます。 これはレッスン1/4です。
「リフレクションによるクラスの調査」レッスンにはどのくらい時間がかかりますか?
ほとんどのCoddyKitレッスンは約5~10分かかります。各レッスンはコンパクトでインタラクティブなので、着実に進歩し、ウェブとアプリ全体で正確に前回の場所から再開できます。
このJava Academyレッスンでコードを書いて実行できますか?
はい。すべてのJava Academyレッスンに組み込みコードエディタが含まれているため、ブラウザでリアルコードを書いて実行し、即座のAIフィードバックを取得できます。ローカル設定は不要です。
このコースのすべてのレッスン
- リフレクションによるクラスの調査
- メソッドの呼び出しとフィールドへのアクセス
- InvocationHandler による動的プロキシ
- リフレクションの性能と代替手段