Java —— 泛型的学习

//使用泛型的优点
/** 
使用泛型的主要优点是能够在编译时而不是运行时检测出错误。泛型类或方法允许用户指定可以
和这些类或方法一起工作的对象类型和一个包含数字的栈对象*/
/*防止不能一起工作的数据类型进行工作*/


//泛型的使用 ClassName<T> e = new ClassName<T>();如:
ArrayList<String> list = new ArrayList<String>();


1.定义泛型类和接口<code>
public class ClassName <E> {
public ClassName() {
//构造方法
}
}
</code>

public interface InterfaceName <E> {


}
2.定义泛型方法


a.基本
public <E> returnVar method(E e) {
//传递参数类型必须合法才不会发生编译错误
}


使用 
E e;
ClassName<E>.method(e) 来调用;


b.受限的泛型类型,将泛型指定为另一种类型的子类型


public <E extends fatherClass> returnVar method(E o1, E o2) {
//此时,只有当参数的传递类型为fatherClass 的子类,才不会发生编译错误


}
说明:
非受限类型<E> 与 <E extends Object> 是一样的


3.其他 
(1)原始类型和向后兼容
a.可以使用泛型类而无需指定具体类型
ClassName e = new ClassName();
等价于
ClassName <Object> = new ClassName<Object>();


原始参数(raw type):不使用类型参数的泛型类
如:max(Comparable o1, Comparable o2) {


}
在Java的早期版本中,允许使用原始类型向后兼容(backward compatibility)


原始类型是不安全的,所以可以将上面的max函数改为
public <E extends Comparable> returnVar max(E o1, E o2) {
//这样的话,要调用max(),则需要 o1 与 o2 同为一种类型才不会发生编译错误
}


(2)通配泛型


a.原因
例如有如下类
public class ClassName {
public static void main(String[] args) {
ClassName1<Integer> e = new ClassName1<Integer>();

method(e);//这里会出现编译错误
}

public static returnVar method(ClassName1<Number> e) {

}
}


b.使用
在调用method(e)时,此时会出现编译错误,原因是:尽管Integer是Number的子类型,但
ClassName1<Integer> 不是ClassName1<Number>的子类。为了避免这个问题,可以使用
通配泛型。有三种形式 
<?>  
<? extends T>
<? super T>


可修改上面程序的错误
public static returnVar method(ClassName1<? extends Number> e) {


}


<?> 为 <? extends Object> 的缩写


<? super T> 表示类型T 或者 T的父类型


(3)消除泛型和对泛型的限制
泛型是使用一种称为类型消除(type erasure)的方法实现的。编译器使用泛型类型信息
来编译代码,但是随后会消除它。
泛型存在于编译时,一旦编译器确认泛型类型安全使用的,就会将它转换为原始类型。


限制


1.不能使用 E e = new E(); 因为运行时泛型类型E是不可用的
2.不能使用 泛型参数创建数组
E[] e = new E[capacity]
可以这样规避
E[] e = (E[] ) new Object[capacity]


说明:会导致一个免疫的编译警告,因为不能保证在运行过程中类型转换能够成功。
 不能使用 泛型类创建数组
 ArrayList<String>[] list = new ArrayList<String>[10];
 规避
 ArrayList<String>[] list = new (ArrayList[String]) new Object[10];
 同理 也会导致一个编译警告
 3.在静态环境下不允许类的参数是泛型类型
 public class ClassName<E> {
public static void m(E o1) {
//illegal
}
public static E o1;//illegal
static {
E o2;//illegal
}
 }
 4.异常类不能是泛型的
 public class MyException<T> extends Exception {
/*
try {
}
catch  (MyException ex){
}
*/
 }
 



  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值