Java 的 Collections(java.util.Collections)类是一个工具类,包含了大量用于在 Java 中处理集合的实用静态方法。在本教程中,我将介绍其中一些最有用的方法。
addAll() 方法可以向集合(通常是 List 或 Set)中添加数量可变的元素。下面是一个调用集合 addAll() 方法的 Java 代码示例:
package com.hxstrive.java_collection;
import java.util.List;
import java.util.ArrayList;
import java.util.Collections;
public class CollectionsAddAllDemo {
public static void main(String[] args) {
// 创建泛型为String的ArrayList
List<String> list = new ArrayList<>();
// 使用Collections.addAll()批量添加元素
boolean allAdded = Collections.addAll(list,
"element 1", "element 2", "element 3", "element 4", "element 5");
// 输出添加结果
System.out.println("所有元素是否添加成功: " + allAdded);
System.out.println("列表中的元素:");
for (String element : list) {
System.out.println("- " + element);
}
// 演示继续添加更多元素
Collections.addAll(list, "element 6", "element 7");
System.out.println("\n添加更多元素后的列表:");
System.out.println(list);
// 演示添加不同类型元素会编译报错
// Collections.addAll(list, 123); // 错误: 不兼容的类型,int无法转换为String
}
}运行结果:
所有元素是否添加成功: true 列表中的元素: - element 1 - element 2 - element 3 - element 4 - element 5 添加更多元素后的列表: [element 1, element 2, element 3, element 4, element 5, element 6, element 7]
binarySearch() 方法可以使用二分查找算法在 List 中搜索元素。在使用 binarySearch() 搜索之前,必须以升序对 List 进行排序。
二分查找算法(Binary Search Algorithm),也称为 “折半查找”,是一种高效的有序数据查找算法。其核心思想是通过不断将 “查找范围减半”,快速缩小目标元素的可能位置,最终定位到目标(或确定目标不存在),适用于已排序的线性数据结构(如数组、有序列表)。
下面是一个使用 binarySearch() 方法搜索 List 的示例:
package com.hxstrive.java_collection;
import java.util.List;
import java.util.ArrayList;
import java.util.Collections;
public class StringListBinarySearch {
public static void main(String[] args) {
// 创建字符串列表并添加元素
List<String> list = new ArrayList<>();
list.add("one");
list.add("two");
list.add("three");
list.add("four");
list.add("five");
// 打印排序前的列表
System.out.println("排序前的列表: " + list);
// 对列表进行排序(按字符串自然顺序)
Collections.sort(list);
System.out.println("排序后的列表: " + list);
// 使用二分查找寻找"four"
int index = Collections.binarySearch(list, "four");
// 输出查找结果
System.out.println("元素\"four\"的索引位置: " + index);
}
}运行结果:
排序前的列表: [one, two, three, four, five] 排序后的列表: [five, four, one, three, two] 元素"four"的索引位置: 1
copy() 方法可以将 List 中的所有元素复制到另一个 List 中。例如:
package com.hxstrive.java_collection;
import java.util.Arrays;
import java.util.List;
import java.util.ArrayList;
import java.util.Collections;
public class CollectionsCopyDemo {
public static void main(String[] args) {
List<String> source = new ArrayList<>(Arrays.asList("a", "b", "c"));
List<String> dest = new ArrayList<>();
// 关键:先填充足够的空元素,确保目标列表容量 >= 源列表
for (int i = 0; i < source.size(); i++) {
dest.add(null); // 填充null作为占位
}
Collections.copy(dest, source); // 此时可正常复制
System.out.println(dest); // 输出 [a, b, c]
}
}Collections.copy() 要求目标列表容量必须 >= 源列表,否则抛出 Source does not fit in dest 异常:
Exception in thread "main" java.lang.IndexOutOfBoundsException: Source does not fit in dest at java.util.Collections.copy(Collections.java:556)
copy() 方法适合覆盖已有元素的场景,不适合动态创建副本。日常开发中,使用 new ArrayList<>(source) 或 addAll() 是更简单安全的列表复制方式。
Collections reverse() 方法可以反转 List 中的元素。下面是一个反转 List 元素的示例:
package com.hxstrive.java_collection;
import java.util.List;
import java.util.ArrayList;
import java.util.Collections;
public class CollectionsReverseDemo {
public static void main(String[] args) {
// 创建字符串列表并添加元素
List<String> list = new ArrayList<String>();
list.add("one");
list.add("two");
list.add("three");
list.add("four");
// 打印反转前的列表
System.out.println("反转前的列表: " + list);
// 调用reverse()方法反转列表元素顺序
Collections.reverse(list);
// 打印反转后的列表
System.out.println("反转后的列表: " + list);
}
}运行结果:
反转前的列表: [one, two, three, four] 反转后的列表: [four, three, two, one]
Collections shuffle() 方法可以对列表中的元素进行洗牌。“洗牌”指将列表中的元素随机重新排列,就像洗牌时将扑克牌打乱顺序一样。例如:
package com.hxstrive.java_collection;
import java.util.List;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Random;
public class CollectionsShuffleDemo {
public static void main(String[] args) {
// 创建字符串列表并添加元素
List<String> list = new ArrayList<String>();
list.add("one");
list.add("two");
list.add("three");
list.add("four");
list.add("five");
System.out.println("洗牌前的列表: " + list);
// 第一次随机洗牌(使用默认随机数生成器)
Collections.shuffle(list);
System.out.println("第一次洗牌后: " + list);
// 第二次随机洗牌(结果通常不同)
Collections.shuffle(list);
System.out.println("第二次洗牌后: " + list);
// 使用指定种子的Random对象进行洗牌
Random fixedRandom = new Random(100); // 固定种子
Collections.shuffle(list, fixedRandom);
System.out.println("指定种子洗牌后: " + list);
}
}运行结果:
洗牌前的列表: [one, two, three, four, five] 第一次洗牌后: [three, four, one, five, two] 第二次洗牌后: [three, two, five, four, one] 指定种子洗牌后: [one, four, two, five, three]
sort() 方法可以对 List 进行排序。例如:示例:
package com.hxstrive.java_collection;
import java.util.List;
import java.util.ArrayList;
import java.util.Collections;
public class CollectionSortDemo {
public static void main(String[] args) {
List<String> list = new ArrayList<String>();
list.add("one");
list.add("two");
list.add("three");
list.add("four");
System.out.println("排序前的列表: " + list);
// 使用Collections.sort()进行自然排序
Collections.sort(list);
System.out.println("排序后的列表: " + list);
}
}运行结果:
排序前的列表: [one, two, three, four] 排序后的列表: [four, one, three, two]
min() 方法可以根据元素的自然排序找到 List 中的最小元素。例如:
package com.hxstrive.java_collection;
import java.util.List;
import java.util.ArrayList;
import java.util.Collections;
public class CollectionsMinDemo {
public static void main(String[] args) {
List source = new ArrayList();
source.add("1");
source.add("2");
source.add("3");
source.add("0");
// 使用Collections.min()获取最小元素(需要强制类型转换,因为列表未使用泛型)
String min = (String) Collections.min(source);
System.out.println("列表中的元素: " + source);
System.out.println("列表中的最小元素: " + min);
// 演示使用泛型的更安全方式
List<String> genericList = new ArrayList<>();
genericList.add("apple");
genericList.add("banana");
genericList.add("cherry");
String minStr = Collections.min(genericList);
System.out.println("\n泛型列表中的元素: " + genericList);
System.out.println("泛型列表中的最小元素: " + minStr);
}
}运行结果:
列表中的元素: [1, 2, 3, 0] 列表中的最小元素: 0 泛型列表中的元素: [apple, banana, cherry] 泛型列表中的最小元素: apple
注意,Collections.min(source) 方法用于获取列表中的最小元素,其比较基于元素的自然顺序(实现 Comparable 接口)。由于示例中的源列表 source 未使用泛型,返回的是 Object 类型,因此需要强制转换为 String。对于字符串元素,最小元素的判断基于字典顺序(Unicode 值比较):
数字字符串比较:"0" < "1" < "2" < "3"
字母字符串比较:"apple" < "banana" < "cherry"(基于首字母的 Unicode 值)
推荐使用泛型列表(如 List<String>),可以避免强制类型转换,使代码更安全简洁。
max() 方法可以根据元素的自然顺序找出 List 中的最大元素。例如:
package com.hxstrive.java_collection;
import java.util.List;
import java.util.ArrayList;
import java.util.Collections;
public class CollectionsMaxDemo {
public static void main(String[] args) {
List source = new ArrayList();
source.add("1");
source.add("2");
source.add("3");
source.add("5");
source.add("4");
// 使用Collections.max()获取最大元素(需强制类型转换,因列表未使用泛型)
String max = (String) Collections.max(source);
System.out.println("列表中的元素: " + source);
System.out.println("列表中的最大元素: " + max);
// 演示泛型列表的用法(更安全,无需类型转换)
List<String> fruitList = new ArrayList<>();
fruitList.add("orange");
fruitList.add("apple");
fruitList.add("watermelon");
String maxFruit = Collections.max(fruitList);
System.out.println("\n水果列表中的元素: " + fruitList);
System.out.println("水果列表中的最大元素: " + maxFruit);
}
}运行结果:
列表中的元素: [1, 2, 3, 5, 4] 列表中的最大元素: 5 水果列表中的元素: [orange, apple, watermelon] 水果列表中的最大元素: watermelon
注意,Collections.max() 方法通过遍历列表比较所有元素,找出自然顺序中最大的元素,适用于所有元素可比较的列表。
replaceAll() 方法可以用另一个元素替换一个元素的所有出现。您可以将要替换的元素和要替换的元素作为参数传递给 replaceAll() 方法。如果有元素被替换,Collections replaceAll() 方法返回 true;如果没有,则返回 false。例如:
package com.hxstrive.java_collection;
import java.util.List;
import java.util.ArrayList;
import java.util.Collections;
public class ReplaceAllExample {
public static void main(String[] args) {
List source = new ArrayList();
source.add("A");
source.add("B");
source.add("A");
// 使用Collections.replaceAll()替换元素
boolean replacedAny = Collections.replaceAll(source, "A", "C");
System.out.println("是否有元素被替换: " + replacedAny);
System.out.println("替换后的列表: " + source);
// 演示替换不存在的元素
boolean replacedNone = Collections.replaceAll(source, "X", "Y");
System.out.println("\n替换不存在的元素时是否有替换: " + replacedNone);
System.out.println("替换不存在元素后的列表: " + source);
}
}运行结果:
是否有元素被替换: true 替换后的列表: [C, B, C] 替换不存在的元素时是否有替换: false 替换不存在元素后的列表: [C, B, C]
执行此示例后,源 List 将包含元素 C、B 和 C。由于 List 中至少有一个元素被替换,因此 replacedAny 变量的值为 true。
Collections replaceAll() 方法使用每个元素的 equals() 方法来确定该元素是否等于要替换的元素。
unmodifiableSet() 方法可以从普通 Java 集合创建不可变(不可修改)的集合。例如:
package com.hxstrive.java_collection;
import java.util.Set;
import java.util.HashSet;
import java.util.Collections;
public class UnmodifiableSetDemo {
public static void main(String[] args) {
// 创建普通的HashSet并添加元素
Set<String> normalSet = new HashSet<>();
normalSet.add("Apple");
normalSet.add("Banana");
normalSet.add("Cherry");
System.out.println("普通集合元素: " + normalSet);
// 创建不可修改的集合视图
Set<String> immutableSet = Collections.unmodifiableSet(normalSet);
System.out.println("不可修改集合元素: " + immutableSet);
// 尝试修改不可修改的集合(会抛出异常)
try {
immutableSet.add("Date");
} catch (UnsupportedOperationException e) {
System.out.println("尝试添加元素到不可修改集合时的异常: " + e.getMessage());
}
try {
immutableSet.remove("Apple");
} catch (UnsupportedOperationException e) {
System.out.println("尝试删除元素时的异常: " + e.getMessage());
}
// 修改原始集合会影响不可修改集合的内容
normalSet.add("Elderberry");
System.out.println("\n原始集合修改后,不可修改集合的内容: " + immutableSet);
}
}运行结果:
普通集合元素: [Apple, Cherry, Banana] 不可修改集合元素: [Apple, Cherry, Banana] 尝试添加元素到不可修改集合时的异常: null 尝试删除元素时的异常: null 原始集合修改后,不可修改集合的内容: [Apple, Cherry, Elderberry, Banana]
到这里,我们介绍了 Collections 工具类中最常用的方法,更多方法的用法请参考 https://docs.oracle.com/javase/8/docs/api/java/util/Collections.html API 文档。