Appearance
Collectors.groupingBy有三种主要的重载形式,下面通过代码示例来详细说明它们的使用。1. 基本形式:
按某个函数进行分组
javaList<String> list = Arrays.asList("apple", "banana", "cherry", "apricot"); Map<Character, List<String>> grouped = list.stream() .collect(Collectors.groupingBy(s -> s.charAt(0))); System.out.println(grouped);输出:
text{a=[apple, apricot], b=[banana], c=[cherry]}说明:
- 功能:按照字符串的首字母将字符串分组。
- 返回类型:
Map<Character, List<String>>,键是字符串的首字母,值是具有相同首字母的字符串集合。
2. 带下游收集器:
除了分组外,还可以对每个组内的元素进行进一步处理,比如计数、求和等。
javaList<String> list = Arrays.asList("apple", "banana", "apple", "cherry", "banana"); Map<String, Long> counts = list.stream() .collect(Collectors.groupingBy( Function.identity(), // 按照字符串分组 Collectors.counting() // 计算每组的元素个数 )); System.out.println(counts);输出:
text{apple=2, banana=2, cherry=1}说明:
- 功能:按字符串进行分组,并计算每个组中字符串的个数。
- 返回类型:
Map<String, Long>,键是字符串,值是该字符串在列表中出现的次数。
3. 带自定义
Map和下游收集器: 除了分组和下游收集器之外,你还可以指定一个自定义的
Map实现类。List<String> list = Arrays.asList("apple", "banana", "cherry", "apricot"); Map<Character, Set<String>> groupedSet = list.stream() .collect(Collectors.groupingBy( s -> s.charAt(0), // 按首字母分组 TreeMap::new, // 使用 TreeMap 作为 Map 实现 Collectors.toSet() // 组内元素使用 Set 存储 )); System.out.println(groupedSet);输出:
text{a=[apple, apricot], b=[banana], c=[cherry]}说明:
- 功能:按首字母分组,并将每个组内的元素存储在
Set中,最终使用TreeMap来存储分组的结果(TreeMap保证按字母顺序排序)。 - 返回类型:
Map<Character, Set<String>>,其中键是字符,值是一个去重的字符串集合。
总结
- 第一种形式:只进行分组,返回
Map<K, List<T>>。 - 第二种形式:除了分组,还可以使用下游收集器(如
counting()、summarizingInt()等),返回Map<K, D>。 - 第三种形式:自定义
Map类型,同时还可以指定下游收集器,返回Map<K, D>。