Java では実行時にすべての型情報が消去されないのはなぜですか? 質問する

Java では実行時にすべての型情報が消去されないのはなぜですか? 質問する

これまでの Java Generics に関する私の明らかな誤解は、Type Erasure によってすべての型情報が削除され、実行時に何も残らないというものでした。最近、私は自分自身に尋ねざるを得ないコード フラグメントに遭遇しました。このハックはどのように機能するのでしょうか? 簡単に説明すると、次のようになります。

import java.lang.reflect.ParameterizedType;
import java.lang.reflect.Type;

public abstract class SuperClass<T> {

    private final Type type;

    protected SuperClass(){
        ParameterizedType parameterizedType =
                (ParameterizedType) getClass().getGenericSuperclass();
        type = parameterizedType.getActualTypeArguments()[0];
    }

    public void tellMyType(){
        System.out.println("Hi, my type parameter is " + type);
    }    
}

そして

public class Example {

    public static void main(String[] args) {
        SuperClass sc = new SuperClass<Integer>(){};
        sc.tellMyType();
    }
}

メインクラスを実行すると、次のようになりますHi, my type parameter is class java.lang.Integer

ここでわかるのは、T の型情報も実行時に利用できるということですが、これは私の当初の理解と矛盾しています。

そこで私の質問は、なぜコンパイラはこれを保持するのかということです。これは何らかの内部 JVM 動作に必要なのでしょうか、それともこの効果について合理的な説明があるのでしょうか。

ベストアンサー1

からhttp://www.artima.com/weblogs/viewpost.jsp?thread=208860:

JVM はジェネリック クラスのインスタンスの実際の型引数を追跡しませんが、ジェネリック クラスのサブクラスの実際の型引数は追跡します。つまり、 new は実行時にはArrayList<String>()単なる new ですArrayList()が、クラスが を拡張する場合ArrayList<String>、JVM はが の型Stringパラメータの実際の型引数であることを認識します。List

あなたの場合、パラメータ化された型の匿名サブクラスを作成しているので、型情報は保持されます。詳細な説明については記事を参照してください。

おすすめ記事