侧边栏壁纸
博主头像
colo

欲买桂花同载酒

  • 累计撰写 1823 篇文章
  • 累计收到 0 条评论

Java泛型基础 - 理解类型擦除和类型安全

2025-12-13 / 0 评论 / 4 阅读

题目

Java泛型基础 - 理解类型擦除和类型安全

信息

  • 类型:问答
  • 难度:⭐

考点

泛型概念,类型擦除,类型安全

快速回答

Java泛型的主要作用是提供编译时类型检查,防止运行时类型转换错误。核心要点:

  • 泛型通过类型参数化增强代码复用和类型安全
  • Java泛型采用类型擦除实现,编译后替换为Object或边界类型
  • 泛型可防止ClassCastException,如List<String>只能添加字符串
## 解析

一、泛型核心原理

Java泛型本质是参数化类型,在编译阶段进行类型检查,运行时通过类型擦除(Type Erasure)实现:

// 编译前
List<String> stringList = new ArrayList<>();
stringList.add("Hello");

// 编译后(类型擦除效果)
List stringList = new ArrayList(); // 类型参数被擦除
stringList.add("Hello"); // 实际存储为Object

类型擦除规则:

  • 无边界泛型(如<T>)擦除为Object
  • 有边界泛型(如<T extends Number>)擦除为边界类型(Number

二、类型安全示例

泛型如何避免类型错误:

// 非泛型代码 - 可能引发ClassCastException
List rawList = new ArrayList();
rawList.add(123);       // 添加Integer
String s = (String) rawList.get(0); // 运行时错误!

// 泛型代码 - 编译时即报错
List<String> safeList = new ArrayList<>();
safeList.add(123);      // 编译错误:类型不匹配
safeList.add("Text");   // 仅允许String类型

三、最佳实践与常见错误

最佳实践:

  • 优先使用泛型集合(如List<T>而非原生List
  • 方法中使用泛型参数:<T> void process(T item) {...}
  • 通配符边界:List<? extends Number>接受Number子类

常见错误:

  • 错误1:尝试创建泛型数组
    // 错误写法!
    T[] arr = new T[10];
    // 正确替代方案:
    List<T> list = new ArrayList<>();
  • 错误2:忽略编译器警告(如未经检查的类型转换)
  • 错误3:运行时获取泛型类型(因类型擦除,list.getClass()无法获得String

四、扩展知识

  • 通配符使用:
    List<?>(未知类型), List<? super Integer>(下限)
  • 类型擦除的例外:通过反射可获取方法签名中的泛型信息(如Method.getGenericParameterTypes()
  • 与C#泛型区别:Java泛型无运行时类型信息,C#保留类型参数