我有一个泛型类,Foo<T>。在Foo的一个方法中,我想获取T类型的类实例,但我无法调用T.class。

使用T.class绕过它的首选方法是什么?


当前回答

我假设,既然你有一个泛型类,你会有一个这样的变量:

private T t;

(此变量需要在构造函数中取值)

在这种情况下,您可以简单地创建以下方法:

Class<T> getClassOfInstance()
{
    return (Class<T>) t.getClass();
}

希望它有帮助!

其他回答

标准方法/解决方法/解决方案是向构造函数中添加类对象,例如:

 public class Foo<T> {

    private Class<T> type;
    public Foo(Class<T> type) {
      this.type = type;
    }

    public Class<T> getType() {
      return type;
    }

    public T newInstance() {
      return type.newInstance();
    }
 }

很多人不知道这个把戏!事实上,我今天刚找到它!它就像一个梦!请查看以下示例:

public static void main(String[] args) {
    Date d=new Date();  //Or anything you want!
    printMethods(d);
}

public static <T> void printMethods(T t){
    Class<T> clazz= (Class<T>) t.getClass(); // There you go!
    for ( Method m : clazz.getMethods()){
        System.out.println( m.getName() );
    }
}

我在抽象泛型类中遇到了这个问题。在这种特殊情况下,解决方案更简单:

abstract class Foo<T> {
    abstract Class<T> getTClass();
    //...
}

以及随后的派生类:

class Bar extends Foo<Whatever> {
    @Override
    Class<T> getTClass() {
        return Whatever.class;
    }
}

实际上,这是可能的(没有外部库!)

以下是我对这个问题的(丑陋但有效的)解决方案:

import java.lang.reflect.TypeVariable;


public static <T> Class<T> getGenericClass() {
    __<T> instance = new __<T>();
    TypeVariable<?>[] parameters = instance.getClass().getTypeParameters(); 

    return (Class<T>)parameters[0].getClass();
}

// Generic helper class which (only) provides type information. This avoids the
//   usage of a local variable of type T, which would have to be initialized.
private final class __<T> {
    private __() { }
}

这是一个有效的解决方案:

@SuppressWarnings("unchecked")
private Class<T> getGenericTypeClass() {
    try {
        String className = ((ParameterizedType) getClass().getGenericSuperclass()).getActualTypeArguments()[0].getTypeName();
        Class<?> clazz = Class.forName(className);
        return (Class<T>) clazz;
    } catch (Exception e) {
        throw new IllegalStateException("Class is not parametrized with generic type!!! Please use extends <> ");
    }
} 

笔记:只能用作超类

必须使用类型化类进行扩展(Child扩展Generic<Integer>)

OR

必须创建为匿名实现(new Generic<Integer>(){};)