一、泛型概述
泛型:JDK1.5的新特性,本质就是数据类型参数化
在泛型出现之前,一个变量的类型能兼容多个类型,就需要将该类型声明成Object
应用场景:
1.泛型类
2.泛型接口
3.泛型方法
二、泛型特点:
1.如果不为泛型指定具体的数据类型,默认为Object类型
2.泛型在编译期就已经确定了类型
3.泛型必须是引用数据类型,不能是基本数据类型
4.泛型可以将一些运行时会发生的问题,提前到了编译期,更利于bug的修改
eg:
//泛型类 <数据类型的形参名>,在使用期间,我们可以给它传递真实类型
class Test<T,T1,T2>{
T a;
T1 b;
T2 c;
public T aa(T x) {
return a;
}
}
//泛型接口
interface Inter<T>{
public void aa(T a);
}
//实现泛型接口
class Impl implements Inter<Long>{
@Override
public void aa(Long a) {
}
}
实现泛型接口时,还是不能确定泛型的类型,用泛型类来实现泛型接口,泛型接口的具体类型就和泛型类的保持一致了;
例如此处,我们给Impl2的T赋值为Integer,接口的T也会变成Integer,
class Impl2<T> implements Inter<T>{
@Override
public void aa(T a) {
}
}
public class GenericType {
//泛型方法 在方法的修饰符和返回值之间有<> 该方法才是泛型方法
public static <N> void aa(N a) {
System.out.println(a);
}
public static void main(String[] args) {
//1 不提前指定泛型的类型,根据参数具体的类型推断出泛型类型
aa(100);
//2 直接指定了泛型的类型
GenericType.<Double>aa(100.5);
Test<Integer,Float,String> test = new Test<>();
test.a = 10;
//此处c的值只能是String,要不然运行时会报错 (体现特点4)
test.c = "10";
// ?:通配符,例如<?> 此处可以是任意类型
Test<Double,Float,?> test2 = new Test<>();
test2.a = 10.5;
System.out.println(test2.c); //(c应是Object类型)
泛型部分不体现多态性
例如需要类型为TT<Number>,提供的类型只能是TT<Number> ,即使是TT<Integer>都不行
TT<Integer> tt = new TT<>();
qq(tt);
TT<Object> t1 = new TT<>(); //TT<>中String、Object、Serializable接口也可 (接口看作类的特殊父类)
qq2(t1);
}
通配符,例如<?> 此处可以是任意类型 (若为<Object>也不可任意类型)
上限定通配符:<? extends A> 此处的类型必须是A或者A的子孙类
下限定通配符:<? super A> 此处的类型必须是A或者A的祖先类
public static void qq(TT<? extends Number> t) {
}
public static void qq2(TT<? super String> t) {
}
}
class TT<P>{
P a;
}