Java Enum 고급 활용

Java Enum은 단순한 상수 그룹 이상의 기능을 제공합니다. 상수별로 다른 동작을 구현하는 방법을 살펴봅니다.

상수별 메서드 구현

switch 문을 사용하지 않고, 각 enum 상수가 자체적으로 메서드를 구현하는 패턴입니다.

기본 구조

public enum Category {
    UNKNOWN {
        @Override
        List<CodeItem> getItems() {
            return null;
        }
    },
    JIO {
        @Override
        List<CodeItem> getItems() {
            return Collections.singletonList(CodeItem.ALL_CHECK);
        }
    },
    NON_JIO_PREPAID {
        @Override
        List<CodeItem> getItems() {
            return Arrays.asList(
                CodeItem.PRE_PLAN,
                CodeItem.PRE_BALANCE,
                CodeItem.PRE_3G4G,
                CodeItem.PRE_2G,
                CodeItem.PRE_CALL_LNS,
                CodeItem.PRE_CALL_LOC,
                CodeItem.PRE_CALL_STD,
                CodeItem.PRE_SMS_LNS,
                CodeItem.PRE_SMS_LOC,
                CodeItem.PRE_SMS_STD
            );
        }
    },
    NON_JIO_POSTPAID {
        @Override
        List<CodeItem> getItems() {
            return Arrays.asList(
                CodeItem.POST_UNBILL,
                CodeItem.POST_BILL,
                CodeItem.POST_3G4G,
                CodeItem.POST_2G,
                CodeItem.POST_RENTAL
            );
        }
    };

    @Nullable
    abstract List<CodeItem> getItems();
}

사용 방법

Category category = Category.NON_JIO_PREPAID;
List<CodeItem> items = category.getItems();

switch vs 상수별 메서드

switch 사용 시 (비권장)

public List<CodeItem> getItems(Category category) {
    switch (category) {
        case UNKNOWN:
            return null;
        case JIO:
            return Collections.singletonList(CodeItem.ALL_CHECK);
        case NON_JIO_PREPAID:
            return Arrays.asList(...);
        case NON_JIO_POSTPAID:
            return Arrays.asList(...);
        default:
            throw new IllegalArgumentException();
    }
}

문제점:

  • 새로운 enum 상수 추가 시 switch 문 수정을 잊기 쉬움
  • 컴파일 타임에 누락 검사 불가

상수별 메서드 사용 시 (권장)

  • 새로운 enum 상수 추가 시 반드시 추상 메서드를 구현해야 함
  • 컴파일 타임에 누락 검사 가능
  • 각 상수의 동작이 해당 상수 선언과 함께 위치

추가 활용 패턴

필드와 함께 사용

public enum Operation {
    PLUS("+") {
        @Override
        public double apply(double x, double y) {
            return x + y;
        }
    },
    MINUS("-") {
        @Override
        public double apply(double x, double y) {
            return x - y;
        }
    },
    TIMES("*") {
        @Override
        public double apply(double x, double y) {
            return x * y;
        }
    },
    DIVIDE("/") {
        @Override
        public double apply(double x, double y) {
            return x / y;
        }
    };

    private final String symbol;

    Operation(String symbol) {
        this.symbol = symbol;
    }

    public String getSymbol() {
        return symbol;
    }

    public abstract double apply(double x, double y);
}

사용 예시

double result = Operation.PLUS.apply(1, 2);  // 3.0
String symbol = Operation.PLUS.getSymbol();  // "+"

정리

상수별 메서드 구현의 장점:

  1. 타입 안전성: 컴파일 타임에 모든 케이스 처리 보장
  2. 가독성: 각 상수의 동작이 선언과 함께 위치
  3. 유지보수성: 새 상수 추가 시 메서드 구현 강제
  4. OCP 준수: Open-Closed Principle에 부합

switch 문이 필요한 곳에서 enum의 상수별 메서드 구현을 고려해 보세요.