这是我最近在一次采访中提出的一个问题,即考生希望看到的添加到Java语言中的东西。人们通常认为Java没有reified generics是一种痛苦,但是当被推送时,候选人实际上无法告诉我他在那里可以实现的目标。

显然,由于Java中允许使用原始类型(以及不安全的检查),因此有可能破坏泛型并以List<Integer>结尾,例如,该String实际上包含List。如果类型信息得到证实,这显然变得不可能。但还必须有更多!

人们是否可以发布他们确实想做的事情的示例,这些示例可以使用通用泛型?我的意思是,显然您可以在运行时获取Class的类型-但是您将如何处理呢?

public <T> void foo(List<T> l) {
   if (l.getGenericType() == Integer.class) {
       //yeah baby! err, what now?

编辑:对此的快速更新,因为答案似乎主要与是否需要传递EnumSet.noneOf(TimeUnit.class)作为参数有关(例如ojit_code)。我一直在寻找一些无法实现的目标。例如:
List<?> l1 = api.gimmeAList();
List<?> l2 = api.gimmeAnotherList();

if (l1.getGenericType().isAssignableFrom(l2.getGenericType())) {
    l1.addAll(l2); //why on earth would I be doing this anyway?

最佳答案

从我几次遇到这种“需求”开始,它最终可以归结为这种构造:

public class Foo<T> {

    private T t;

    public Foo() {
        this.t = new T(); // Help?
    }

}

T具有默认构造函数的情况下,这在C#中有效。您甚至可以通过 typeof(T) 获得运行时类型,并通过 Type.GetConstructor() 获得构造函数。

常见的Java解决方案是将Class<T>作为参数传递。
public class Foo<T> {

    private T t;

    public Foo(Class<T> cls) throws Exception {
        this.t = cls.newInstance();
    }

}

(它不一定需要作为构造函数参数传递,因为方法参数也可以,上面只是一个示例,为了简洁起见,省略了try-catch)

对于所有其他通用类型构造,可以在反射的帮助下轻松地解析实际类型。下面的问题解答说明了用例和可能性:
  • Get generic type of java.util.List
  • How to get the generic type at runtime?
  • Get actual type of generic type argument on abstract superclass
  • 09-04 02:21
    查看更多