使用泛型机制编写的程序代码要比那些杂乱地使用Object变量,然后再进行强制类型转换的代码更具有更好的安全性和可读性,泛型对集合类尤其有用
一.我们为什么使用泛型程序设计
泛型程序设计意味着编写的代码可以被很多不同类型的对象所重用
1.类型参数的好处
在Java增加泛型类之前,泛型程序设计是使用继承来实现,ArrayList类只维护一个Object引用的数组,这种方法有两个问题,当获取一个值的时候必须进行强制类型转换
ArrayList files = new ArrayList();
String filename = (String)files.get(0);
此外我们可以向数组列表中添加任何类的对象,但是当强制将某个结果不是它的类型转换为其他类型,那么就会产生一个错误
这边泛型提供了一个更好的解决方法:类型参数(使得程序具有更好的可读性和安全性)
ArrayList<String> files = new ArrayList<String>();//这样更具有可读性,让人一看就知道是String的对象的
Java7后构造函数中可以省略泛型类型
ArrayList<String> files = new ArrayList<>();
现在编译器就可以利用好这个信息了,也就是说当调用get时就不用进行强制类型转换了,编译器知道它返回的类型是String,而不是Object
String filename = files.get(0);
现在files.add(new File(".."));这句话就不能通过编译了,因为类型不符合,出现编译时错误比类在运行时发生类的强制类型转换异常更好
2.谁想成为泛型程序员
一个泛型Java程序员的任务就是预测出所用的类的未来可能有的所有的用途
通配符类型,他解决了类似 将ArrayList<Manager>中的所有元素添加到ArrayList<Employee>中去,但是不能将ArrayList<Employee>添加到ArrayList<Manager>这种问题
二.定义简单的泛型类
一个泛型类就是一个具有一个或是多个类型变量的类,下面会来使用一个简单的Pair类当为例子
public class Pair<T> {
private T first;
private T second;
public Pair() {
first = null;second = null;
}
public T getFirst() {
return first;
}
public T getSecond(){
return second;
}
public void setFirst( T newValue){
first = newValue;
}
public void setSecond( T newValue){
second = newValue;
}
}
这个类引入了一个类型变量T,用尖括号<>括起来,并放在一个类后面,泛型类可以有多个类型变量
如Pair<T,U>{};
类定义中的类型变量指定方法的返回变量以及域和局部变量的类型
类型变量应该使用大写形式,而且比较短的,在Java中变量E表示集合的元素类型,K和V分别表示关键字和值的类型
然后用具体的类型替换变量就可以实例化泛型类型了,如Pair<String>
换一句话来说,就是泛型类可以看成普通类的工厂类
三.泛型方法
前面已经定义了一个泛型类,下面是来定义一个带有类型参数的简单方法
public static <T> T getMiddle(T...a) {
return a[a.length/2];
}
在泛型方法中,类型变量放在修饰符之前,返回类型的前面,泛型方法可以定义在普通类中,也可以定义在泛型类中,
在调用一个泛型方法的时候需要在方法名之前的尖括号放入具体的类型,如下面:
String middle = ArrayAlg.<String>getMiddle("jab","qq","hosjo");
四.类型变量的限定
有时,类和方法需要对类型变量加以约束,比如有时我们