【Java 你应该知道的】 泛型01
来源:互联网 发布:王者荣耀输入法软件 编辑:程序博客网 时间:2024/05/17 07:57
为什么使用泛型
通过泛型可以定义类型安全的数据结构,而无须使用实际的数据类型,这能够显著提高性能并得到更高质量的代码。我们可以简单总结为“可扩展”,“更安全”。
回忆一下Java中的集合,以List为例,如果使用时不指定泛型,存储的数据会被包装成Ojbect类型。从List中读取的数据也是装箱后的Object,使用前还需要通过强制类型转换拆箱成相应类型。这样做不仅效率低,还存在风险(强制类型转换错误)。
// 定义集合未指定泛型 List datas = new ArrayList<>(); // 存储的数据会被保存成Object datas.add("a1"); datas.add(123); // 读取的数据也是Object,需要强制类型转换 for (Object obj : datas) { String str = (String) obj; // 编译可通过,但运行异常 System.out.println(str); }
上面的案例,会报异常异常,因为类型转换错误。
Exception in thread "main" java.lang.ClassCastException: java.lang.Integer cannot be cast to java.lang.String
泛型类
再看一个没有使用泛型的做法,定义一个简单的Box类。
public class Box { private String obj; public Box(String obj) { super(); this.obj = obj; } public String getObj() { return obj; } public void setObj(String obj) { this.obj = obj; } }
上面的Box类里面现在只能装入String类型的元素,今后如果我们需要装入Integer等其他类型的元素,还必须要另外重写一个Box,代码得不到复用。如果将String改成Object,又会涉及类型转换的问题。很多初学者在封装工具类的时候,为了达到通用型,会采用Object的方式,其实这样做是不对的。
泛型实JDK1.5提出的新特效,以上的问题可以采用泛型类的方式加以处理。泛型类的写法是在类名后面加上 <T>
,这里的T是泛型形参,可以代表任意的引用类型。使用该类的时候,必须指明具体的引用类型,即泛型实参。
public class Box<T> { private T t; public Box(T t) { super(); this.t = t; } public T getT() { return t; } public void setT(T t) { this.t = t; } }
Box<String> box = new Box<String>("abc"); String obj = box.getT(); Box<Integer> box2 = new Box<Integer>(2); Integer obj2 = box2.getT();
几点说明:
- 泛型不支持基本数据类型,只能是引用类型
- 泛型可以有多个,用逗号分隔,如
<T,V>
等 - 泛型形参可以使用T、E、K、V等形式,一般根据意义来选择
- T: Type(类型)
- E: Element (元素)
- K: Key(键)
- V: Value(值)
- N: Number(数值类型)
泛型方法
泛型方法的实现方式也比较简单,只需要在方法返回类型前面加上泛型形参即可。 泛型方法使得该方法能独立于类而产生变化。如果使用泛型方法可以取代将整个类泛型化,那么建议只使用泛型方法。
public static <T> void show(T t) { System.out.println(t.toString()); }
Utils.show("abc"); Utils.show(123);
泛型接口
看到这里,我相信大家能大体理解了泛型的作用了。在实际开发中,泛型最多的应用场景应该是在接口中使用了,我们称为泛型接口。比如当我们定义Person类或者Animal类的使用,都有eat的动作,我们会把eat的行为抽象成接口。但吃什么不确定,这个时候就可以使用上泛型接口了。
public interface IEatable<T> { void eat(T t); }
public class Person implements IEatable<String>{ @Override public void eat(String t) { System.out.println("吃了" + t); } }
public class Animal<T> implements IEatable<T>{ @Override public void eat(T t) { System.out.println("吃了" + t.toString()); } }
- 【Java 你应该知道的】 泛型01
- 【Java 你应该知道的】泛型02
- java 你应该知道的
- 你应该知道的JAVA面试题
- 你应该知道的JAVA面试题
- 你应该知道的JAVA面试题
- 你应该知道的
- Java 应该知道的
- cookies你应该知道的
- session你应该知道的
- 你应该知道的Unicode
- 你应该知道的print
- 你应该知道的ThreadPoolExecutor
- 你应该知道的统计学
- 你应该知道的 8 个Java 的领军人物
- 你应该知道的 8个Java 的领军人物
- 你应该知道的 8个Java 的领军人物
- 你应该知道的 8个Java 的领军人物
- 一个求数组中最大元素的函数模板
- linux之Vim文档编辑
- LeetCode
- HDU
- 网络编程基础集
- 【Java 你应该知道的】 泛型01
- html5 css js轮播图动画
- Fluent FIDAP v8.7_简体中文教程7.rar
- ASP.net button验证
- String,StringBuffer,StringBuilder的区别
- 编写shell脚本遇到的问题
- (11)XML入门
- include<stdlib.h>与include“kdtree”的本质区别
- spring boot整合ElascticSearch