반응형

groupingBy

공통 코드

@AllArgsConstructor
@Data
public class User {
    private String type;
    private String status;
    private String name;
    private int age;
}
List<User> users = List.of(
    new User("google", "inactive", "john", 20),
    new User("google", "inactive", "tom", 25),
    new User("google", "active", "tyler", 30),
    new User("kakao", "active", "jane", 35)
);

Simple Grouping by a Single Column

Map<String, List<User>> userMap = users.stream()
    .collect(Collectors.groupingBy(user -> user.getType()));

assertEquals(3, userMap.get("google").size());
assertEquals(1, userMap.get("kakao").size());

Modifying the Returned Map Value Type

Map<String, Set<User>> userMap = users.stream()
    .collect(Collectors.groupingBy(
        user -> user.getType(),
        Collectors.toSet()
    ));

assertEquals(3, userMap.get("google").size());
assertEquals(1, userMap.get("kakao").size());

Grouping by Multiple Fields

Map<String, Map<String, List<User>>> userMap = users.stream()
    .collect(Collectors.groupingBy(
        user -> user.getType(),
        Collectors.groupingBy(user -> user.getStatus())
    ));

assertEquals(2, userMap.get("google").size());
assertEquals(1, userMap.get("google").get("active").size());
assertEquals(2, userMap.get("google").get("inactive").size());
assertEquals(1, userMap.get("kakao").size());
assertEquals(1, userMap.get("kakao").get("active").size());

Getting the Average from Grouped Results

Map<String, Double> userMap = users.stream()
    .collect(Collectors.groupingBy(
        user -> user.getType(),
        Collectors.averagingInt(user -> user.getAge())
    ));

assertEquals(25.0, userMap.get("google"));
assertEquals(35.0, userMap.get("kakao"));

Getting the Maximum from Grouped Results

Map<String, Optional<User>> userMap = users.stream()
    .collect(Collectors.groupingBy(
        user -> user.getType(),
        Collectors.maxBy(Comparator.comparingInt(user -> user.getAge()))
    ));

assertEquals(30, userMap.get("google").get().getAge());
assertEquals(35, userMap.get("kakao").get().getAge());

Getting a Summary for an Attribute of Grouped Results

Map<String, IntSummaryStatistics> userMap = users.stream()
    .collect(Collectors.groupingBy(
        user -> user.getType(),
        Collectors.summarizingInt(user -> user.getAge())
    ));

assertEquals(3, userMap.get("google").getCount());
assertEquals(75, userMap.get("google").getSum());
assertEquals(20, userMap.get("google").getMin());
assertEquals(30, userMap.get("google").getMax());

assertEquals(1, userMap.get("kakao").getCount());
assertEquals(35, userMap.get("kakao").getSum());
assertEquals(35, userMap.get("kakao").getMin());
assertEquals(35, userMap.get("kakao").getMax());

Aggregating multiple Attributes of a Grouped Result

@AllArgsConstructor
@Data
public class UserStatistics {
    private int total;
    private double ageAverage;
}
Map<String, UserStatistics> userMap = users.stream()
    .collect(Collectors.groupingBy(
        user -> user.getType(),
        Collectors.collectingAndThen(
            Collectors.toList(),
            users -> new UserStatistics(
                users.size(),
                users.stream().collect(Collectors.averagingInt(user -> user.getAge()))
            )
        )
    ));

assertEquals(3, userMap.get("google").getTotal());
assertEquals(25.0, userMap.get("google").getAgeAverage());
assertEquals(1, userMap.get("kakao").getTotal());
assertEquals(35.0, userMap.get("kakao").getAgeAverage());

Mapping Grouped Results to a Different Type

@AllArgsConstructor
@Data
public class UserDto {
    private String name;
    private int age;
}
Map<String, List<UserDto>> userMap = users.stream()
    .collect(Collectors.groupingBy(
        user -> user.getType(),
        Collectors.mapping(
            user -> new UserDto(user.getName(), user.getAge()),
            Collectors.toList()
        )
    ));

assertEquals(3, userMap.get("google").size());
assertEquals(1, userMap.get("kakao").size());
Map<String, String> userMap = users.stream()
    .collect(Collectors.groupingBy(
        user -> user.getType(),
        Collectors.mapping(
            user -> user.getName(),
            Collectors.joining(", ", "UserNames : [", "]")
        )
    ));

assertEquals("UserNames : [john, tom, tyler]", userMap.get("google"));
assertEquals("UserNames : [jane]", userMap.get("kakao"));

Modifying the Return Map Type

Map<String, List<User>> userMap = users.stream()
    .collect(Collectors.groupingBy(
        user -> user.getType(),
        () -> new LinkedHashMap<>(),
        Collectors.toList()
    ));

assertEquals(LinkedHashMap.class, userMap.getClass());
assertEquals(3, userMap.get("google").size());
assertEquals(1, userMap.get("kakao").size());

Concurrent groupingBy Collector

Map<String, List<User>> userMap = users.parallelStream()
    .collect(Collectors.groupingByConcurrent(user -> user.getType()));

assertEquals(ConcurrentHashMap.class, userMap.getClass());
assertEquals(3, userMap.get("google").size());
assertEquals(1, userMap.get("kakao").size());

참고

반응형

'Development > Java' 카테고리의 다른 글

[Java] JUnit4  (0) 2021.11.23
[Java] Hash Algorithm  (0) 2021.11.17
[Java] Shell Command 실행하기  (0) 2021.08.28
[Java] Date  (0) 2021.07.24
[Java] CompletableFuture  (0) 2021.03.30

+ Recent posts