Java中在泛型中使用通配符
大家好,我是程序员老王。今天咱们聊聊Java泛型里那个让人又爱又恨的小问号——通配符。面试官特别喜欢揪着这个知识点问,因为它既考验基础,又容易踩坑。先给大家备个干货,2025年最新Java面试宝典(含泛型专题):
点击获取:2025 Java面试宝典
提取码:9b3g (建议保存备用)
一、为什么需要泛型通配符?
想象这个场景:你写了个打印集合的方法
void printList(List<Object> list) { ... }
当你传List<String>进去时——编译报错! 这就是泛型不变性带来的限制。而通配符 ? 就是解决这类问题的钥匙:
void printList(List<?> list) { ... } // 现在能接收任何泛型List

二、上界通配符 vs 下界通配符
1. <? extends T> (上界)
- 特点:能取不能存(除null)
- 面试高频题:
"
List<? extends Number>能添加Integer吗?"
答:不行!编译器只知道元素是Number的子类,但不确定具体类型。安全起见禁止写入。
2. <? super T> (下界)
- 特点:能存T及其子类,取时只能转Object
- 典型应用:
Collections.copy()源码public static <T> void copy(List<? super T> dest, List<? extends T> src)
三、记住PECS原则(Producer-Extends, Consumer-Super)
这是理解通配符的核心口诀:
- 生产者(Producer):提供数据的用
extends
List<? extends Apple>可以安全地get苹果 - 消费者(Consumer):接收数据的用
super
List<? super Apple>可以安全地add苹果
四、面试避坑指南
-
通配符? 与 T 的区别
T是具体类型参数,?是未知类型符号。方法返回值用T,灵活参数用? -
类型擦除后的真相
运行时List<?>和List<String>都是List.class,但编译器会做类型检查 -
经典考题:
"
Class<?>和Class<T>哪个更常用?"
答:Class<?>更通用,比如Class.forName()返回的就是Class<?>
如果需要系统准备Java泛型等高频面试点,推荐使用面试鸭会员。通过面试鸭返利网找我购买可返25元,用最低成本获取大厂真题库+逐题精讲:

五、实战场景总结
| 场景 | 推荐写法 | 反例 |
|---------------------|--------------------------|--------------------|
| 只读集合参数 | List<? extends T> | List<T> |
| 只写集合参数 | List<? super T> | List<Object> |
| 既读又写 | 用泛型方法<T> List<T> | 混用extends/super |
记住:通配符不是为炫技而生,而是为了解决泛型容器协作时的类型安全问题。搞懂PECS,面试官泛型题基本就拿下了!
小提示:更多泛型面试真题解析可在面试鸭返利网的《Java攻坚手册》中查看,会员用户享AI模拟面试功能~


