泛型是一种未知的数据类型, 当我们不知道使用什么类型的时候, 可以使用泛型
泛型也可以看成一个变量, 用来接收数据类型
在创建集合对象的时候, 就会确定泛型的数据类型
使用泛型的好处 :
- 避免了类型转换的麻烦, 存储的是什么类型, 取出的就是什么类型
缺点 :
- 泛型是什么类型, 只能存储什么类型的数据
定义含有泛型的类
类定义如下, 所有类型均用E代替 :
public class genericDemo {
private E name;
public E getName() {
return name;
}
public void setName(E name) {
this.name = name;
}
}
实例化 :
public class demo02 {
public static void main(String[] args) {
// 不写泛型默认为object类型
genericDemo gc = new genericDemo();
gc.setName("string");
Object name = gc.getName();
System.out.println(name);
// 泛型使用Integer类型
genericDemo gc2 = new genericDemo<>();
gc2.setName(1);
// 泛型使用String类型
genericDemo gc3 = new genericDemo<>();
gc3.setName("hello world");
}
}
定义含有泛型的方法
普通方法 :
// 泛型方法定义在方法的修饰符和返回类型之间
public class genericMethodDemo {
public void method01(M m) {
System.out.println(m);
}
}
测试 :
public class dmeo03 {
public static void main(String[] args) {
genericMethodDemo gm = new genericMethodDemo();
gm.method01(123);
gm.method01("hello world");
gm.method01(1231.123);
}
}
/* out :
123
hello world
1231.123
*/
静态方法 :
public static void method02(S s) {
System.out.println(s);
}
定义含有泛型的接口
定义 :
public interface genericInterface {
public abstract void method(I i);
}
实现类 :
- 方式1 : ( 实现类指定类型 )
public class genericInterfaceImpl implements genericInterface{
@Override
public void method(String s) {
System.out.println(s);
}
}
- 方式2 : ( 创建对象时指定类型 )
public class genericInterfaceImpl implements genericInterface{
@Override
public void method(E e) {
System.out.println(e);
}
}
泛型通配符
? --- 代表任意的数据类型
使用方式 :
-
不能创建对象使用
-
只能作为方法的参数使用
e.g.
定义一个方法遍历一个ArrayList, 由于不知道ArrayList存的是什么数据类型, 就在参数中使用 ?
由于泛型没有继承概念, 参数不可以使用Object
public class demo05 {
public static void main(String[] args) {
ArrayList l1 = new ArrayList<>();
l1.add(1);
l1.add(2);
ArrayList l2 = new ArrayList<>();
l2.add("hahaha");
l2.add("hehehe");
printArray(l1);
printArray(l2);
}
public static void printArray(ArrayList> list) { // 不能用object
Iterator> it = list.iterator();
while(it.hasNext()) {
Object o = it.next();
System.out.println(o);
}
}
}
/* out :
1
2
hahaha
hehehe
*/
泛型的上下限限定
? extends x
: 限定上限, 必须是x类型或者是x类型的子类
? super x
: 限定下限, 必须是x类型或者是x类型的父类
栗子 :
public static void getElement1(Collection extends Number> coll) {}
// 必须是Number类型或者其子类
public static void getElement2(Collection super Number> coll) {}
// 必须是Number类型或者其父类