public static void printElement(ArrayList<?> al) {
Iterator<?> it = al.iterator();
while (it.hasNext()) {
System.out.println(it.next().toString());
}
}
使用T:
public static <T> void printElement(ArrayList<T> al) {
Iterator<T> it = al.iterator();
while (it.hasNext()) {
T next = it.next();
System.out.println(next.toString());
}
}
5. 泛型方法
上面的代码里也看到了泛型方法了,泛型方法,是在调用方法的时候指明泛型的具体类型。
5.1 语法
public <T> T genericMethod(Class<T> tClass)throws InstantiationException ,
IllegalAccessException{
T instance = tClass.newInstance();
return instance;
}
6.2 super的使用
public static void main(String[] args) {
/**
* List<? super Fruit> 表示具有任何Fruit超类型的列表,列表的类型至少是一个 Fruit 类型,
* 因此可以安全的向其中添加Fruit 及其子类型。
*
* 由于List<? super Fruit>中的类型可能是任何Fruit 的超类型,无法赋值为Fruit的子类型Apple的List<Apple>.
*/
List<? super Fruit> flist = new ArrayList<Fruit>();
flist.add(new Fruit());
flist.add(new Apple());
flist.add(new RedApple());
// compile error:
// List<? super Fruit> flist1 = new ArrayList<Apple>();
// 因为,List<? super Fruit>中的类型可能是任何Fruit 的超类型,
// 所以编译器无法确定get返回的对象类型是Fruit, 还是Fruit的父类Food 或 Object.compile error:
// Fruit item = flist.get(0);
}
7. 泛型数组
java中是"不能创建一个确切的泛型类型的数组"的。
也就是说下面的这个例子是不可以的:
List<String>[] ls = new ArrayList<String>[10];
而使用通配符创建泛型数组是可以的,如下面这个例子:
List<?>[] ls = new ArrayList<?>[10];
这样也是可以的:
List<String>[] ls = new ArrayList[10];
看看sun文档提供一个例子:
List<String>[] lsa = new List<String>[10]; // Not really allowed.
Object o = lsa;
Object[] oa = (Object[]) o;
List<Integer> li = new ArrayList<Integer>();
li.add(new Integer(3));
oa[1] = li; // Unsound, but passes run time store check
String s = lsa[1].get(0); // Run-time error: ClassCastException.
这种情况下,由于JVM泛型的擦除机制,在运行时JVM是不知道泛型信息的,所以可以给oa[1]赋上一个ArrayList而不会出现异常,但是在取出数据的时候却要做一次类型转换,所以就会出现ClassCastException,如果可以进行泛型数组的声明,上面说的这种情况在编译期将不会出现任何的警告和错误,只有在运行时才会出错。
List<?>[] lsa = new List<?>[10]; // OK, array of unbounded wildcard type.
Object o = lsa;
Object[] oa = (Object[]) o;
List<Integer> li = new ArrayList<Integer>();
li.add(new Integer(3));
oa[1] = li; // Correct.
Integer i = (Integer) lsa[1].get(0); // OK