通常我们在看一些源码时,发现全是T、?,晕乎乎的:sob:。于是,把泛型掌握好十分重要!
Java泛型(generics)是JDK5中引入的一个新特性,泛型提供了编译时类型安全检测机制,该机制允许程序员在编译时检测到非法的类型。
泛型的本质是参数化类型,也就是说所操作的数据类型被指定为一个参数。
泛型有什么好处?写个例子一目了然:
我们要封装一个消息响应类:
publicclassResultimplementsSerializable{//响应码Integercode;//是否成功Booleansuccess;//返回体数据Useruser;publicResult(Integercode,Booleansuccess,Useruser){this.code=code;this.success=success;this.user=user;}@OverridepublicStringtoString(){return"Result{"+"code="+code+",success="+success+",user="+user+'}';}publicstaticvoidmain(String[]args){Useruser=newUser(1,"Tony");Resultresult=newResult(200,true,user);System.out.println(result);}}classUserimplementsSerializable{Integerid;Stringname;publicUser(Integerid,Stringname){this.id=id;this.name=name;}@OverridepublicStringtoString(){return"User{"+"id="+id+",name='"+name+'\''+'}';}}Result{code=200,success=true,user=User{id=1,name='Tony'}}进程已结束,退出代码0呼~这样这个反应体就可以返回请求状态和用户信息了。可现在需求又需要返回关于手机的信息,那我们又得封装一个能返回手机信息的响应类了...到后面还有衣服、鞋子...那不得累死?这时候泛型登场了:
第一次接触可能看不太明白,下面就详细讲解
你可以写一个泛型方法,该方法在调用时可以接收不同类型的参数。根据传递给泛型方法的参数类型,编译器适当地处理每一个方法调用。
比如说这是一个用来打印数组的泛型方法:
比如这个方法
这些标记并不是限定只有对应的类型才能使用,即使你统一使用A-Z英文字母的其中一个,编译器也不会报错。之所以又不同的标记符,这是一种**约定。**在开发中很多规则都是一种约定,它能提高我们代码的可读性,方便团队见的合作开发
写个完整的例子:
publicclassTFunction{publicstaticvoidmain(String[]args){//创建各种类型的数组Integer[]intArray={1,2,3,4,5};Double[]doubleArray={1.1,2.2,3.3,4.4};Character[]charArray={'H','E','L','L','O'};System.out.println("整型数组元素为:");printArray(intArray);//传递一个整型数组System.out.println("\n双精度型数组元素为:");printArray(doubleArray);//传递一个双精度型数组System.out.println("\n字符型数组元素为:");printArray(charArray);//传递一个字符型数组}//泛型方法privatestatic
这边就不举例子了,因为开篇的例子就是封装了一个泛型类,当时不太理解的可以再回去看一下
我们一般可以使用来承接所有的引用类型,搬运一个菜鸟上的例子:
publicclassGenericTest{publicstaticvoidmain(String[]args){List
这是**泛型上边界:**只有T对象的子类可以被传入
如果是extendsC,那么只有D和E允许被传入,否则会编译报错
这是**泛型下边界:**只有T对象的父类可以被传入
如果是superD,那么只有C和A允许被传入,否则会编译报错
不知道看到这里,有没有疑惑。T和好像作用差不多啊,有什么区别?
这里解释一下,T一般作为泛型参数,而是更多是用来一个不确定的引用类型,意会一下吧~~~
重头戏!!
那么问题就来了,Object好像可以代替泛型的功能啊!所有能用到泛型的地方Object都可以!
其实,在JDK5之前,都是用的Object,但其存在很多的问题,JDK5之后便引入了泛型
Object是所有类的父类,在编码过程中就难免出现类型转化问题,且在编译阶段不会报错,到了运行阶段才暴露问题,大大降低了程序的安全性和健壮性!
举例之前说一些转型的分类:
Animalcat=newCat();向下转型
将父类对象强转为其子类实例:
Animalcat=newCat();CatanotherCat=(Cat)cat;所以当我们使用Object作为泛型来使用时,不仅写起来麻烦,还要不停的进行类型转化,还很容易出现问题,很逊的诶~
举个例子看看:
利用Object定义了一个数字变量,我们常识将其向下转型为Integer和String。将一个数字转型为字符串是一件荒唐的事情,可编译器并不能察觉这件事,直到程序运行了起来...
类型转换异常!!!
泛型的出现,当类型转化出现问题的时候,在编译阶段就会暴露出来。解决了Object存在的诸多问题,让代码更加优雅,程序更加安全,更加健壮。