JDK5增加了泛型机制, 泛型的优点 : 可以提高代码的复用性.
一、泛型的定义形式
Java泛型只用于编译期间,编译完成擦除类型信息, 在运行其间JVM知道泛型所代表的类型.
优秀博客 : Java的类型擦除
1.1 泛型类
public interface List<E> extends Collection<E> {
// ...
}
引入一个类型变量E, 用尖括号
<>
括起来, 并放在类名的后面. 其中泛型类可以有多个类型变量, 但第一个域和第二个域使用不同的类型:
public class Test<T, U> { … }
类定义中的类型变量指定 方法的返回类型以及域和局部变量的类型.
其中泛型中的E, T, U 分别代表什么,为何起这个名字?
类型变量使用大写形式,且比较短,其中E,T,U…是为了见名知意.
E -> Element(集合中使用,存放的是元素,代表元素类型)
T -> Type(Java类)
K -> Key(键) V -> Value(值)
N -> Number(数值类型)
? -> 不确定的java类型(无限制通配符类型)
如果尖括号中包含多个类型变量,一般取相邻的大写字母.
1.2 泛型方法
public class ArrList {
public static <T> T[] toArray(T[] a);
}
类型变量放在修饰符(这里是public static)的后面,返回类型的前面.
泛型方法可以定义在普通类中,也可以定义在泛型类中.
1.3 泛型参数的引用
类型参数的优点: 使得程序具有更好的可读性和安全性.
ArrayList< String > list = new ArrayList< String >();
Java SE 7及以后的版本中,构造函数中可以省略泛型类型;(后面可以省略不写). ArrayList<String> list = new ArrayList<>();
二、泛型中的上下界限符
List<? super T>
List<? extends T>
优秀博客 : Java 之泛型通配符 ? extends T 与 ? super T 解惑
2.1 <? extends T>
泛型参数必须是T类型或T类型的子类
一个变量或通配符可以有多个限定. 例如:
T extends Comparable & Serializable
限定类型用"&"分隔,而都好用来分隔类型变量.
2.2 <? super T>
泛型参数类型必须是此类型或此类型的超类型(父类型),直至Object
2.3 PECS原则
摘自H大直面java第136期
如果要从集合中读取类型T的数据, 并且不能写入, 可以使用 ? extends 通配符; (Producer Extends)