泛型集合的定义及使用
引入
什么是泛型、为什么要引入泛型、泛型类和泛型方法的使用
实例泛型:
创建对象时,为类所定义的泛型,进行参数化赋值。
- 类:创建对象时,为类所定义的泛型,进行参数化赋值
- 接口:实现接口时,为接口所定义的泛型,进行参数化赋值
静态泛型:
- 定义在方法的返回值类型前面:、、>、> 可应用在形参列表、返回值两种场景上,不单单可以规范泛型,还可以语义化返回值。
- 定义在方法的形参列表当中:<?>、<? extends Object>、<? super Integer>,不支持使用& 只能应用在形参列表上,规范泛型。
1 概述
一种约束---规范类型(常用名字:E = Elememt、T = Type、K = Key、V = Value),将类型的明确工作提前到对象的创建以及方法调用,防止程序不安全泛型 :将类型的明确工作提前到对象的创建以及方法调用,防止程序不安全;参数化类型、类型安全的集合,强制集合的类型必须一致;
特点:
- 编译时即可检查,而非运行时抛出异常
- 访问时,不必类型转换也就是拆箱
- 不同泛型之间引用不能相互赋值,泛型不存在多态。(左泛型不可为右父类)
2 泛型的好处
- 将运行时期异常提前到了编译时期;
- 在遍历集合时,避免了强制类型转换;
- 解决了程序黄色警告线的问题------>提高了程序的安全性;
public static void main(String[] args) {
//创建一个ArrayList集合对象
ArrayList<String> array = new ArrayList<String>() ;//后面:泛型推断
//添加元素
array.add("kaka") ;
array.add("hello") ;
array.add("java") ;
array.add("javaee") ;
//遍历
Iterator<String> it = array.iterator() ;
while(it.hasNext()) {
String s = it.next() ;
System.out.println(s);
}
}
- 使用泛型集合时注意类型要保持一致,否则会出现类型转化异常(ClassCastException)
2.1 ArrayList集合存储自定义对象,加入泛型
需求:使用ArrayList集合存储自定义对象Student,加入泛型
1)定义一个学生类
2)创建集合对象 ArrayList
3)创建5个学生
5)将5个学生添加到集合中
6)创建迭代器
7)利用迭代器遍历集合
8)利用get(int index)+size()相结合的方式遍历
/*
* 学生类
*/
public class Student {
private String name ;
private int age ;
public Student() {
super();
// TODO Auto-generated constructor stub
}
public Student(String name, int age) {
super();
this.name = name;
this.age = age;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
@Override
public String toString() {
return "Student [name=" + name + ", age=" + age + "]";
}
}
public static void main(String[] args){
//创建一个ArrayList集合
ArrayList<Student> array = new ArrayList<Student>() ;
//创建学生对象
Student s1 = new Student("曹操",35) ;//后知后觉
Student s2 = new Student("蒋干",25) ;//不知不觉
Student s3 = new Student("诸葛亮",30) ;//先知先觉
array.add(s1) ;
array.add(s2) ;
array.add(s3) ;
//迭代器
Iterator<Student> it = array.iterator() ;
while(it.hasNext()) {
Student s = it.next() ;
System.out.println(s.getName()+"---"+s.getAge());
}
System.out.println("----------------------------");
//普通for循环:get(int index)+size()相结合
for(int x = 0 ; x < array.size() ; x ++) {
Student s = array.get(x) ;
System.out.println(s.getName()+"---"+s.getAge());
}
}
3 泛型的应用
泛型主要应用在集合中:
- 定义在类中
- 定义在接口中
- 定义在方法中
3.1 泛型类
把泛型定义在类上
格式:
public class 类名<泛型类型1,…>
泛型类型必须是引用类型
/*
* 使用泛型:提高程序的安全性:将泛型定义类上
*/
public class ObjectTool<T>{
//成员变量
private T obj ;
//获取功能
public T get() {
return obj ;
}
//设置功能
public void set(T obj) {
this.obj = obj ;
}
}
/*
* 将泛型定义在类上 测试类
*/
public static void main(String[] args) {
//创建ObjectTool类的对象
ObjectTool<String> ot = new ObjectTool<String>() ;
//设置数据
ot.set("卡卡");
//获取数据
String s = ot.get() ;
System.out.println("姓名是:"+s);
ObjectTool<Integer> ot2 = new ObjectTool<Integer>() ;
//设置数据
ot2.set(28);
Integer i = ot2.get() ;
System.out.println("年龄是:"+i);
}
3.2 泛型方法
把泛型定义在方法上
格式:
- public <泛型类型> 返回类型 方法名(泛型类型 .)
public class ObjectTool<T>{
//将泛型定义在方法上
public <T> void show(T t) {
System.out.println(t);
}
}
public static void main(String[] args) {
//创建ObjectTool类的对象
ObjectTool ot = new ObjectTool() ;
ot.show("hello");
ot.show(true);
ot.show(100);
ot.show(12.34);
}
3.3 泛型接口
把泛型定义在接口上
格式:
- public interface 接口名<泛型类型1…>
3.1 实现类已经明确数据类型
/*
* 定义在接口上
*/
public interface Inter<T> {
public abstract void show(T t);
}
/*
* 测试类
*/
public class InterDemo {
public static void main(String[] args) {
//接口多态
//第一种
Inter i = new InterImpl();
i.show("kaka");//kaka
}
}
/*
* 接口子实现类
*/
public class InterImpl implements Inter<String>{
public void show(String t) {
// TODO Auto-generated method stub
System.out.println(t);
}
}
3.2 子实现类没有明确数据类型
/*
* 定义在接口上
*/
public interface Inter<T> {
public abstract void show(T t);
}
/*
* 测试类
*/
public class InterDemo {
public static void main(String[] args) {
//不明确数据类型
Inter<Integer> i1 = new InterImpl<Integer>();
i1.show(100);//100
Inter<String> i2 = new InterImpl<String>();
i2.show("kaka");//kaka
}
}
/*
* 接口子实现类
*/
public class InterImpl<T> implements Inter<T>{
@Override
public void show(T t) {
// TODO Auto-generated method stub
System.out.println(t);
}
}
4. 高级泛型_通配符
关于泛型的通配符号:
- <?>:任意Java类型(Object),可以自定义的类型,或者是JDK提供的任意Java类;
- <? extends E>:向下限定E类型以及其他子类;
- <? super E>:向上限定E类型以及其他的父类;
public class Generic{
public static void main(String[] args) {
//<?>
//创建集合类型Collection集合
Collection<?> c1 = new ArrayList<Object>();
Collection<?> c2 = new ArrayList<Animal>();
Collection<?> c3 = new ArrayList<Dog>();
Collection<?> c4 = new ArrayList<Cat>();
//<? extends E>
Collection<? extends Animal> c5 = new ArrayList<Animal>();
Collection<? extends Animal> c6 = new ArrayList<Dog>();
Collection<? extends Animal> c7 = new ArrayList<Cat>();
// Collection<? extends Animal> c8 = new ArrayList<Object>();错误
//<? super E>
Collection<? super Animal> c9 = new ArrayList<Object>();
Collection<? super Dog> c10 = new ArrayList<Animal>();
Collection<? super Cat> c11 = new ArrayList<Animal>();
// Collection<? super Animal> c12 = new ArrayList<Dog>();错误
}
}
class Animal{
}
class Dog extends Animal{
}
class Cat extends Animal{
}
- 注:在开发过程中,直接在创建集合的时候给定具体的存储类型
Collection<String> c = new ArrayList<String>();