Java Generics WildCard: <? extend Number> vs <T extensions Number>



这两个函数之间有什么区别?

static void gPrint(List<? extends Number> l) {
    for (Number n : l) {
        System.out.println(n);
    }
}
static <T extends Number> void gPrintA(List<T> l) {
    for (Number n : l) {
        System.out.println(n);
    }
}

我看到了同样的输出。

在这种情况下没有区别,因为T再也不用了。

声明T的原因是,您可以再次引用它,从而将两个参数类型或一个返回类型绑定在一起。

区别在于使用通配符时不能引用T

你现在不在,所以"没有区别",但以下是你可以使用T来产生区别的方法:

static <T extends Number> T getElement(List<T> l) {
    for (T t : l) {
        if (some condition)
            return t;
    }
    return null;
}

这将返回与传入的内容相同的类型。例如,它们都将编译:

Integer x = getElement(integerList);
Float y = getElement(floatList);

T是一个有界类型,即无论使用什么类型,都必须坚持使用扩展Number的特定类型,例如,如果将Double类型传递给列表,则不能将其传递给Short类型,因为T的类型是Double,并且列表已经受该类型的约束。相反,如果使用?wildcard),则可以使用扩展Number的"任意"类型(将ShortDouble都添加到该列表中)。

当您使用T时,您可以在List上执行所有类型的操作。但当你使用时,你不能执行添加。

T-与具有完全访问权限的对象引用相同
?-给予部分访问

static void gPrint(List<? extends Number> l) {
 l.add(1); //Will give error
for (Number n : l) {
    System.out.println(n);
}
static <T extends Number> void gPrintA(List<T> l) {
l.add((T)1); //We can add
for (Number n : l) {
    System.out.println(n);
}

相关内容

最新更新