Java 泛型
注:Java泛型面试题来源于百度资源,习题解析来源于课本人,若有不足之处,请批评指正。
1、Java中的泛型是什么?使用的好处?
Java泛型就是我们在声明或使用某个类型时,同时给出类型参数。在声明时,给出的类型参数称为形式参数,在使用类型时,给出的参数称为实际类型参数。
例如:
如我们想要定义一个Student类,程序为:public class Student { } ,这里体现的是声明一个类,所以如果使用泛型,我们应该给这个类一个形式参数。
public class Student<T>{ },这里的T就是形式类型参数。当我们使用这个类的时候,如 Student s = new Student (); 想要给这个形式类型参数传递一个String类型的实际参数。
这可以通过 Student <String > s = new Student<>();的方式将String传递给T。
使用泛型的好处有两个:(1)解决了不安全问题(2)解决了繁琐问题
(1)非泛型的不安全性
以List集合为例。我们首先声明一个集合对象 List list = new ArrayList(); 在我们没加入泛型之前,该集合允许添加Object类型元素。基于工作的需要,某位程序员想要向这个集合中添加 String类型的元素,添加之后还需以String类型输入。可是在工作过程中由于程序员的疏忽将一个Integer类型的元素添加到这个集合中
list.add("a");
list.add("b");
list.add(12);
当然此时系统并不会报错,因为这个集合本来就是容纳Object类型的。当程序员从这个集合提取元素时,由于任然想要String类型,因此就必须对提取的每个元素进行强制类型转换(这是因为虽然元素添加之前是String或是其它类型,但是当添加到Object类型集合后,就都变成Object类型了)。
String s1 =(String) list.get(0);
String s2=(String)list.get(1);
String s3=(String)list.get(2);
注意了list.get(2) 所获取的元素是Integer类型的12,它是没有办法转化为String类型的,当运行时系统就会提示错误。
如果我们使用类泛型 List <String> list = new ArrayList<>();当我们向其中添加 Integer类型数据时,在编译期间系统就会提示我们错误,不可添加。
因此使用泛型可以解决安全问题,(需要特别注意的是在编译期间出错,和运行时出错所造成的后果是相差很大的)。
(2)解决了繁琐问题
对于上述案例,如果不使用泛型,需要程序员每次在提取元素时都要进行类型强转,这样十分繁琐,因此使用泛型,在添加元素之前就规定该集合是String类型集合,那么输出
元素也就一定是String类型。
2、Java泛型是如何工作的?什么是类型檫除?泛型檫除的方式有哪些?
Java泛型与C++是不同,java泛型是通过檫除的方式进行的。
泛型的类型参数信息仅仅保留在编译期间,编译过后,所有的类型信息将会丢失,即泛型的类型安全检查也只能发生在编译期间,编译过后生成的字节码文件中不会保留任何实际类型信息。
泛型檫除的方式:
(1)对于参数化类型(使用泛型时提供实际类型参数称为参数化类型):擦除后之后使用原生类型进行代替。
如: Student<String > s = new Studen<>t(); 檫除以后 Student s =new Student();
(2)对于上界 Student<T extends Ball> s = new Student<>(); 檫除以后 Student<Ball> s = new Student<>();
(3)对于无界 <T> Student<T> s =new Student<>() ; 檫除以后 Student<Object> s =new Student<>();
(4)对于含有多个上界 使用第一个上界做替换
Student<T extends Ball&Sleep&Eat> s =new Student<>(); 檫除以后 Student<Ball> s =new Student<>();
浙公网安备 33010602011771号