----------------------android培训、java培训、期待与您交流! ----------------------
jdk1.5以前集合存在的问题就是一个集合中对存入集合元素的类型不做严格要求,这在取出元素时是很危险的
import java.util.ArrayList;
import java.util.List;
publicclass GernericTest {
publicstaticvoid main(String[] args){
int sum =0;
List list =new ArrayList();
list.add(1);
list.add(2);
list.add(3);
list.add(4);
list.add("string");
for(int i=0;i<list.size();i++){
sum = sum + (Integer)list.get(i);
System.out.println(list.get(i));
}
}
}
运行异常Exception in thread "main" java.lang.ClassCastException: java.lang.String cannot be cast to java.lang.Integer
at test.GernericTest.main(GernericTest.java:17)
这是在添加集合的元素时没有对元素的类型进行约束
jdk1.5的集合希望在定义集合时明确表示要向集合添加哪种类型的数据
import java.util.ArrayList;
import java.util.List;
publicclass GernericTest {
publicstaticvoid main(String[] args){
int sum =0;
ArrayList<Integer> list =new ArrayList<Integer>();
list.add(1);
list.add(2);
list.add(3);
list.add(4);
//list.add("string");
for(int i=0;i<list.size();i++){
sum = sum + list.get(i);
System.out.println(list.get(i));
}
}
}
这里已经明确表示要添加到list 的类型是Integer,所以在list.add("string")是就无法通过编译,而在sum = sum + list.get(i);也无需进行强制类型转换。
泛型的内部原理及应用
泛型是提供给javac编译器使用的,可以限定集合中输入的数据类型,让编译器过滤源程序中的非法输入,编译器编译带类型的集合时会去除掉“类型”信息,使程序的运行效率不受影响。对于参数化的泛型类型,getClass()方法的返回值和原始类型完全一样,由于编译生成的 字节码回去除掉泛型类型的信息,只要能跳过编译器,就可以往某个泛型集合加入其他的类型的数据。
import java.util.ArrayList;
import java.util.List;
publicclass GernericTest {
publicstaticvoid main(String[] args){
List list =new ArrayList();
List<Integer> listInteger =new ArrayList<Integer>();
List<String> listString =new ArrayList<String>();
System.out.println(list.getClass() == listInteger.getClass());
System.out.println(listInteger.getClass() == listString.getClass());
}
}
会打印出true
import java.util.ArrayList;
import java.util.List;
publicclass GernericTest {
publicstaticvoid main(String[] args) throws Exception{
List<Integer> listInteger =new ArrayList<Integer>();
listInteger.getClass().getMethod("add", Object.class).invoke(listInteger, "string");
System.out.println(listInteger.get(0));
}
}
会打印出string
这就在Integer中添加了String。
泛型常识
1:泛型术语
ArrayList称为原始类型
整个ArrayList<E>称为泛型类型
ArrayList<E>中的<>念typeof
ArrayList<E>中的E称为类型变量或者类型参数
整个ArrayList<Integer>称为参数化的类型
ArrayList<Integer>中的Integr称为类型参数的实例或实际类型参数
2:参数化类型和原始类型的兼容性
参数化的类型可以引用一个原始类型的对象,但编译报告警告,例如:
List<Integer> listInteger = new ArrayList();
原始类型可以引用一个参数化类型的对象,编译报告警告,例如:
List listInteger0 = new ArrayList<Integer>();
3:参数化的类型不考虑类型参数的继承关系
List<Ingeger> listInteger = new ArrayList<Object>();
List<Object> listInteger0 = new ArrayList<Integer>();
全部报错
4:在创建数组实例时,数组的元素不能使用参数化的类型
List<Integer> listInteger[] = new ArrayList<Integer>[10];
----------------------android培训、java培训、期待与您交流! ----------------------
详细请查看:http://edu.csdn.net/heima