关于泛型以及它们在这个问题背后真正做了什么有一个很好的讨论,所以我们都知道Vector<int[]>是一个整数数组的向量,HashTable<String, Person>是一个键是字符串和值Person的表。 然而,令我困惑的是Class<>的用法。

java类class也应该有一个模板名(或者是eclipse中的黄色下划线告诉我的)。我不知道我应该在里面写什么。Class对象的全部意义是当您没有关于对象的全部信息时,用于反射等。为什么它让我指定哪个类的类对象将持有?我显然不知道,否则我不会使用Class对象,我会使用特定的对象。


当前回答

摘自Java文档:

[…] 更令人惊讶的是,class已经被泛化了。类字面量现在用作类型标记,提供运行时和编译时类型信息。这就启用了一种静态工厂的风格,例如新的AnnotatedElement接口中的getAnnotation方法:

<T extends Annotation> T getAnnotation(Class<T> annotationType); 

这是一个泛型方法。它从参数中推断出类型形参T的值,并返回一个适当的T实例,如下面的代码片段所示:

Author a = Othello.class.getAnnotation(Author.class);

在使用泛型之前,您必须将结果强制转换为Author。此外,您也没有办法让编译器检查实际参数是否表示Annotation的子类。[…]

我从来没用过这种东西。有人知道吗?

其他回答

再举一个例子,Class的泛型版本(Class<T>)允许编写如下所示的泛型函数。

public static <T extends Enum<T>>Optional<T> optionalFromString(
        @NotNull Class<T> clazz,
        String name
) {
    return Optional<T> opt = Optional.ofNullable(name)
            .map(String::trim)
            .filter(StringUtils::isNotBlank)
            .map(String::toUpperCase)
            .flatMap(n -> {
                try {
                    return Optional.of(Enum.valueOf(clazz, n));
                } catch (Exception e) {
                    return Optional.empty();
                }
            });
}

只要使用牛肉类:

public <T> T beefmarshal( Class<beef> beefClass, InputBeef inputBeef )
     throws JAXBException {
     String packageName = docClass.getPackage().getBeef();
     JAXBContext beef = JAXBContext.newInstance( packageName );
     Unmarshaller u = beef.createBeef();
     JAXBElement<T> doc = (JAXBElement<T>)u.beefmarshal( inputBeef );
     return doc.getBeef();
}

正如其他答案所指出的那样,有很多很好的理由来解释为什么这个类是通用的。然而,很多时候,您无法知道Class<T>要使用的泛型类型。在这些情况下,您可以简单地忽略黄色的eclipse警告,或者使用Class<?>……我就是这么做的;)

摘自Java文档:

[…] 更令人惊讶的是,class已经被泛化了。类字面量现在用作类型标记,提供运行时和编译时类型信息。这就启用了一种静态工厂的风格,例如新的AnnotatedElement接口中的getAnnotation方法:

<T extends Annotation> T getAnnotation(Class<T> annotationType); 

这是一个泛型方法。它从参数中推断出类型形参T的值,并返回一个适当的T实例,如下面的代码片段所示:

Author a = Othello.class.getAnnotation(Author.class);

在使用泛型之前,您必须将结果强制转换为Author。此外,您也没有办法让编译器检查实际参数是否表示Annotation的子类。[…]

我从来没用过这种东西。有人知道吗?

一开始会让人困惑。但它在以下情况下会有所帮助:

class SomeAction implements Action {
}

// Later in the code.
Class<Action> actionClass = Class.forName("SomeAction"); 
Action action = actionClass.newInstance();
// Notice you get an Action instance, there was no need to cast.