Java-泛型基础入门

1 篇文章 0 订阅
本文详细介绍了Java泛型的概念,包括泛型类、泛型接口和泛型方法的用法。同时,解释了泛型类型的特性,如类型擦除和不支持多态性。此外,还探讨了泛型的通配符、边界以及它们在实际编程中的应用场景。通过对泛型上限和下限的设定,可以限制泛型参数的类型范围。最后,文章提到了类型擦除导致的泛型信息在运行时丢失的问题及其原因。
摘要由CSDN通过智能技术生成

泛型解析

泛型概念

泛型是jdk1.5及以上才可以使用的特性/语法,本质就是类型参数化(Parameterized by types)

泛型种类

java中的泛型分为三种使用方法

  • 泛型类
  • 泛型接口
  • 泛型方法
  1. 泛型类,如果泛型参数定义在类上面,那么这个类就是一个泛型类,在这个类中,就可以使用这个T代表某一种类型,这个T的具体类型是什么将由使用时来确定

    class Student<T>{...}
    
  2. 泛型接口,如果泛型参数定义在接口上面,那么这个接口就是一个泛型接口,在接口中就可以使用T来代表某一个类型.

    interface Action<T>{...}
    
  3. 泛型方法,如果泛型参数定义在方法上面,那么这个方法就是一个泛型方法

    // 该方法传入一个T类型的参数返回一个T类型的参数
    public <T> T test(T t){...}
    

泛型的类型

//在编译期间,ArrayList<Integer>和ArrayList<Object>是俩个不同的类型,并且没有子父类型的关
系
ArrayList<Object> list = new ArrayList<Integer>();

注意: = 号两边的所指定的泛型类型,必须是要一样的,泛型类型指的是<>中所指定的类型.

虽然Integer是Object的子类,但是ArrayList和

ArrayList之间没有子父类型的关系,他们就是两个不同的类型.

也就是说,两个类型,如果是当做泛型的指定类型的时候,就没有多态的特点了

通配符

public void test1(Collection<Integer> c){}
public void test2(Collection<String> c){}
public void test3(Collection<Object> c){}

test1 只能接收泛型是Integer类型的集合对象
test2 只能接收泛型是String类型的集合对象
test3 只能接收泛型是Object类型的集合对象

原因:由于泛型之间的类型之间没有多态,所以泛型类型必须一致

解决方法:可以使用通配符?来辨识泛型的父类型

public void test(Collection<?> c){}

使用?所带来的新问题

Collection<?> c = new ArrayList<String>();
// 编译报错,因为c的泛型是?,所以编译器也不知道是什么类型,所以编译器不允许使用c来添加新数据
c.add("hello");
// 通过,集合中一定存的是引用类型,所有的引用都有一个共有的值null,所以一定能添加
c.add(null);

注意: 虽然使用?的集合不能在往其中添加新的数据,但是可以遍历集合取出数据

泛型边界

在默认情况下,泛型的类型可以任意设置的,只要是引用类型就可以

如果在泛型种使用extends和super关键字,可以对泛型的类型进行限制.即:规定泛型的上限和下限.

  1. 泛型的上限:

    例如: List<? extends Number> list

    将来引用list就可以接受泛型是Number或者Number子类型的List集合对象

  2. 泛型的下限:

    例如: List<? super Number> list

    将来引用list就可以接收泛型是Number或者Number父类型的List集合对象

  3. extends 和 super对比

    使用extends可以定义泛型的【上限】,这个就表示将来泛型所接收的类型【最大】是什么类型。

    可以是这个最大类型或者它的【子类型】。

    使用super可以定义泛型的【下限】,这个就表示将来泛型所接收的类型【最小】是什么类型。可

    以是这个【最小类型】或者它的【父类型】。

使用场景

  1. 在声明泛型类或者泛型接口的时候可以使用extends,但不能使用super
  2. 在声明泛型方法的时候可以使用 extends,但不能使用super
  3. 在声明变量的时候可以使用extends,也可以使用super

类型擦除

泛型类型仅仅存在于编译期间,编译后的字节码和运行时不包含泛型信息,所有的泛型类型映射到同一份字节码.

由于泛型是jdk1.5才加入到java语言特性的,java让编译器擦除掉关于泛型类型的信息,这样使得Java可以向后兼容之前没有使用泛型的类库和代码,因为在字节码层面是没有泛型概念的.

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值