PHpullh
학습 라이브러리/Java/불변 컬렉션 & record 조합

JAVA · 함수형/Stream

불변 컬렉션 & record 조합

Java 16+ Record와 불변 컬렉션으로 함수형 스타일의 안전한 데이터 파이프라인을 구축합니다.

함수형/Stream중급RecordList.copyOfunmodifiablefunctionalstream

핵심 설명

Java 16+ Record와 불변 컬렉션으로 함수형 스타일의 안전한 데이터 파이프라인을 구축합니다.

Java code

import java.util.*;
import java.util.stream.*;

// Record + 불변 컬렉션
record Order(int id, String customer, List<String> items, double total) {
    // compact constructor
    public Order {
        items = List.copyOf(items);  // 방어적 복사 → 불변
        if (total < 0) throw new IllegalArgumentException("합계는 양수");
    }

    // 복사 & 수정 패턴 (with-er)
    public Order withTotal(double newTotal) {
        return new Order(id, customer, items, newTotal);
    }
}

public class FunctionalStyle {
    public static void main(String[] args) {
        var orders = List.of(
            new Order(1, "Alice", List.of("책", "펜"), 45000),
            new Order(2, "Bob",   List.of("노트북"), 1200000),
            new Order(3, "Alice", List.of("마우스", "키보드"), 150000),
            new Order(4, "Carol", List.of("모니터"), 800000)
        );

        // 고객별 총 구매액
        Map<String, Double> byCustomer = orders.stream()
            .collect(Collectors.groupingBy(
                Order::customer,
                Collectors.summingDouble(Order::total)));

        // 100만원 이상 고객
        byCustomer.entrySet().stream()
            .filter(e -> e.getValue() >= 1_000_000)
            .sorted(Map.Entry.<String,Double>comparingByValue().reversed())
            .forEach(e -> System.out.printf("%s: %,.0f원%n",
                e.getKey(), e.getValue()));

        // 모든 아이템 평탄화
        List<String> allItems = orders.stream()
            .flatMap(o -> o.items().stream())
            .distinct()
            .sorted()
            .collect(Collectors.toUnmodifiableList());
        System.out.println("전체 상품: " + allItems);

        // Record copy-with 패턴
        var discounted = orders.stream()
            .map(o -> o.withTotal(o.total() * 0.9))
            .collect(Collectors.toList());
        discounted.forEach(o ->
            System.out.printf("주문 #%d: %,.0f원%n", o.id(), o.total()));
    }
}

학습 팁

List.copyOf()는 원본 컬렉션의 불변 복사본을 반환합니다. Record의 compact constructor에서 사용하면 외부에서 내부 컬렉션을 수정할 수 없게 됩니다.

주의할 점

List.of()는 null 원소를 허용하지 않습니다. null이 가능한 컬렉션은 Collections.unmodifiableList(new ArrayList())를 사용하세요.

자주 묻는 질문

불변 컬렉션 & record 조합란 무엇인가요?

Java 16+ Record와 불변 컬렉션으로 함수형 스타일의 안전한 데이터 파이프라인을 구축합니다.

불변 컬렉션 & record 조합 학습 시 주의할 점은 무엇인가요?

List.of() 는 null 원소를 허용하지 않습니다. null이 가능한 컬렉션은 Collections.unmodifiableList(new ArrayList ()) 를 사용하세요.