NotionNext
NotionNext
编程爱好者
/互联网从业者
/知识分享博主
认知决定态度,态度决定选择,选择决定人生

Java中的泛型

NotionNext - 2023-4-17 - Technical / Java / 后端
发布于:2023-4-17|最后更新: 2023-8-29|
type
status
date
slug
summary
tags
category
icon
password

为什么需要泛型(Generics)?

  • 之前实现过一个 int 类型的MyArrayList,但是现在有一个新的需求?
    • 编写支持字符串类型的MyArrayList?
    • 编写支持long类型的MyArrayList?
    • 编写支持User类型的MyArrayList?
    • 未来可能有更多的类型。。。
  • 你总不可能每一个类型的MyArrayList都写一遍吧
  • 在 java 1.5 之前这种事情是普遍发生的

泛型Generics

  • JDK 5引入的新特性
  • 语法:<数据类型>,其中数据类型必须是引用类型
  • 可用于类,接口,方法中
  • 本质:参数化类型
    • 数据类型被指定成为一个参数类型
  • 好处:
    • 提供了编译时类型安全检测机制
    • 极大增强Java语言的类型系统和抽象能力
  • 泛型类
  • 泛型接口
  • 泛型方法

Java泛型实现时面临的问题

  • 后向兼容:还需要支持原来无泛型的容器吗?
  • 不得不这样做:二进制后向兼容性是明确写入Java语言规范的严肃承诺 JDK 1.0 编译出来的 class 文件,JDK19也要支持
  • 面临的选择:
    • 需要泛型化的容器类型,以前的保持不变,新写一套支持泛型化的代码 — C#的选择
    • 直接把已有的类型泛型化(类型擦除) — Java的选择

类型擦除

  • 类型擦除式 V.S 具现化式
  • 类型擦除带来的问题
    • 无法对泛型进行实例判断,没法知道泛型到底属于什么
    • 无法创建泛型数组
    • 无法创建泛型对象
  • 类型擦除之后,通过 signature 保留一些类型信息,通过反射等手段获取

泛型通配符

  • 无限定通配符 - ?
    • 无限制通配符 ? : List<?> list 表示list可以持有任意类型的元素
  • 上界通配符 - ? extends T
    • 上界通配符 ? extends T : List<? extends T> list 表示list可以持有T类型的子类元素
  • 下界通配符 - ? super T
    • 下界通配符 ? super T : List<? super T> list 表示list可以持有T类型的父类元素

PECS原则 - Producer Extends Consumer Super

  • Producer Extends
    • 从集合中读取类型T的数据(集合是生产者),使用通配符 ?extends T
  • Consumer Super
    • 往集合中添加类型T的数据(集合是消费者),使用通配符 ?super T

MyArrayList支持泛型

Java中的排序Java集合之ArrayList