Java 集合 API 中的绝大多数(甚至可以说全部)组件,都支持通过泛型指定元素类型。在本教程中,我将具体演示如何为几种常见的集合类型配置泛型;通过这些示例,你将能掌握在 Java 集合 API 中使用泛型的核心方法。需要说明的是,本文的重点是 “泛型在集合中的应用”,不会展开讲解 Java 泛型的通用语法、原理等基础内容。
为 Java 集合设置泛型类型时,核心操作需在声明集合引用变量时完成。以下示例中,我们将集合(Collection)与具体实现类(HashSet)的泛型类型均指定为 String —— 这一约束意味着该集合只能存储 String 类型的实例,无法添加其他类型的对象。例如:
package com.hxstrive.java_collection; import java.util.Collection; import java.util.HashSet; import java.util.Iterator; public class GenericCollectionDemo { public static void main(String[] args) { // 声明并实例化泛型为String的集合 Collection<String> stringCollection = new HashSet<String>(); // 向集合添加String类型元素(合法操作) stringCollection.add("Apple"); stringCollection.add("Banana"); stringCollection.add("Cherry"); // 尝试添加非 String 类型元素(编译时会报错) // stringCollection.add(123); // 错误: 不兼容的类型: int无法转换为String } }
现在,该 stringCollection 只能包含字符串实例。如果试图添加其他内容,或将集合中的元素转换为 String 以外的任何其他类型,编译器会报错。
当你为 Java 集合指定了泛型类型时,该泛型类型也适用于 iterator() 方法返回的迭代器。下面的示例说明了如何获得一个设置了泛型类型的迭代器,以及迭代泛型迭代器中的元素:
package com.hxstrive.java_collection; import java.util.Collection; import java.util.HashSet; import java.util.Iterator; public class GenericIteratorExample { public static void main(String[] args) { // 创建泛型为String的集合并添加元素 Collection<String> stringCollection = new HashSet<>(); stringCollection.add("Java"); stringCollection.add("Generics"); stringCollection.add("Iterator"); // 获取泛型为String的迭代器 Iterator<String> iterator = stringCollection.iterator(); // 迭代泛型迭代器中的元素 System.out.println("迭代器遍历结果:"); while (iterator.hasNext()) { // 无需类型转换,直接获取String类型元素 String element = iterator.next(); // 可以直接调用String的方法,编译时类型安全 System.out.println("元素: " + element + ", 长度: " + element.length()); } // 演示迭代过程中安全删除元素 iterator = stringCollection.iterator(); // 重新获取迭代器 while (iterator.hasNext()) { String element = iterator.next(); if (element.length() > 6) { iterator.remove(); // 删除长度大于6的元素 System.out.println("\n已删除元素: " + element); } } // 打印删除后的集合 System.out.println("\n删除后的集合元素:"); for (String str : stringCollection) { System.out.println(str); } } }
运行结果:
迭代器遍历结果: 元素: Java, 长度: 4 元素: Iterator, 长度: 8 元素: Generics, 长度: 8 已删除元素: Iterator 已删除元素: Generics 删除后的集合元素: Java
注意,泛型集合的 iterator() 方法会返回与集合相同泛型类型的迭代器(Iterator<String>),调用 iterator.next() 时无需强制类型转换,直接得到 String 类型的元素,这得益于泛型的类型信息传递。迭代器的泛型类型与集合保持一致,确保了从集合获取元素到处理元素的全流程类型安全。
你也可以使用新的 for 循环迭代上述集合,如下所示:
package com.hxstrive.java_collection; import java.util.Collection; import java.util.HashSet; public class GenericForLoopDemo { public static void main(String[] args) { // 创建泛型为String的集合并添加元素 Collection<String> stringCollection = new HashSet<>(); stringCollection.add("Apple"); stringCollection.add("Banana"); stringCollection.add("Cherry"); stringCollection.add("Date"); // 使用增强for循环迭代泛型集合 System.out.println("集合中的元素及其长度:"); for (String stringElement : stringCollection) { // 直接使用String类型的方法,无需类型转换 System.out.println("元素: " + stringElement + ",长度: " + stringElement.length()); } // 演示基于泛型的业务逻辑处理 int totalLength = 0; for (String stringElement : stringCollection) { totalLength += stringElement.length(); } System.out.println("\n所有元素的总长度: " + totalLength); // 演示筛选操作 System.out.println("\n长度大于5的元素:"); for (String stringElement : stringCollection) { if (stringElement.length() > 5) { System.out.println("- " + stringElement); } } } }
运行结果:
集合中的元素及其长度: 元素: Apple,长度: 5 元素: Cherry,长度: 6 元素: Date,长度: 4 元素: Banana,长度: 6 所有元素的总长度: 21 长度大于5的元素: - Cherry - Banana Process finished with exit code 0
注意,增强 for 循环会自动利用集合的泛型信息,变量 stringElement 直接被声明为 String 类型。循环过程中可以直接调用 String 类的方法(如 length()),无需进行类型转换,编译时即保证类型安全。相比非泛型集合的遍历,这种方式消除了 ClassCastException 的风险,代码可读性更高,无需在循环体内进行类型转换的额外操作。