반응형
LottoRank라는 Enum을 정의해서 사용하고 있습니다.
- View쪽에서 메시지를 순서대로 활용하기 위해서 Enum을 정렬하는 방법들을 소개하고자 합니다.
위 메서드를 활용해서 우테코에서 작성한 실행 결과 예시를 출력하려고 합니다.
모든 로또를 관리하는 Class에서 로또 순위를 Key로, 해당 순위가 몇번 나왔는 Count값을 가지는 Value로 저장된 Map을 반환하는 메서드가 있습니다.
View쪽에서 이 Map을 통해서 실행 결과 예시에 맞게 출력해줘야 되는데 keySet()으로 뽑을 때 어떻게 데이터 순서를 보장해줘야 할까요?
- Comparable을 활용할 수 있지 않을까?
- Enum 클래스의 values()를 뽑고 정렬하면 되지 않을까?
Enum의 Comparable
- enum은 이미 상수의 선언 순서로 구현하고 있다고 주석에 적혀있네요!!
- enum의 Comparable의 comapreTo 메소드는 final이라서 compareTo 메소드를 enum에서 오버라이드하여 사용할 수 없습니다.
그렇다면 어떻게 재정의할 수 있을까...?
Comparator의 compare 메소드는 오버라이드하여 사용 가능하기 때문에 enum의 순서를 관리하고 싶다면 클래스를 새로 생성하여 Comparator 을 구현하면 된다.!!
그럼 테스트 해봅시다!!!
- 테스트 통과!!!!
더 찾아보니 EnumMap()이라는게 있었습니다!! Holy Moly~
HashMap 은 hash 값을 계산하여 table 을 제어하는 형태로 데이터를 관리합니다. 이에 비해 EnumMap 은 열거형 상수가 정의된 순서를 가지고, 배열의 index 만 가져오면 되기 때문에 상대적으로 대부분의 경우에 성능이 더 좋다고 할 수 있습니다.
EnumMap 은 HashMap 과 같이 thread safe 하지 않습니다. 따라서 멀티쓰레드 환경에서 여러 쓰레드가 접근할 수 있다면, 동기화를 위한 처리를 해주어야 합니다. 이를 위해 SynchronizedMap 을 사용할 수 있습니다.
출처
생성자로 key type(enum) 을 넘겨주면, enum 에 정의된 열거형 상수의 개수만큼 내부적으로 Object 배열을 생성하고 keyType이라는 멤버변수에 Enum 클래스 타입을 셋팅합니다.
조심할 점이 있는데요🥹🥹
- put에 Null이 들어가면 java.lang.NullPointerException: Cannot invoke "Object.getClass()" because "key" is null 예외가 발생하지만.. get과 remove에서는 삼항 연산자로 null이 들어오면 null을 반환하네요ㅜ
put()메서드에 typeCheck()메서드를 잠깐 확인해보면 key에 Null이 들어오면 NPE가 발생하고 아닌 경우에는 생성자에 의해서 초기화 시켜줬던 keyType과 비교해서 저장하는 것을 볼 수 있습니다.
바로 테스트 작성합시다.
- EnumMap은 Enum에서 final로 정의된 상수 선언 순서로 정렬되어 있는것을 볼 수 있다.
EnumMap은 시작부터 데이터의 사이즈가 enum으로 제한되기 때문에 문제가 발생할 수 없습니다.
Enum 타입의 키를 사용할때는 성능 및 기능상 잇점이 많은 EnumMap 을 사용해 봅시다.
출처 - https://www.manty.co.kr/bbs/detail/develop?id=61
나의 Enum 코드
- 우테코에 OutpuView에 의존하는 정렬 순서라고 생각이 들지만 Comparator를 생성하고 HashMap을 사용하는 것 보다 EnumMap의 성능 이점을 더 좋다고 생각했습니다.
그렇게 저는 여러개의 Lotto를 관리하는 클래스에서 로또 순위와 순위의 개수를 가지고 있는 Map을 반환할 수 있었고
Output View에서 정렬된 keySet()을 사용할 수 있었습니다!
시간 되시는 분들은 EnumSet도 공부하면 좋을거 같습니다 ㅎㅎ!! 시간 내주셔서 감사합니다
EnumSet 은 enum에 대해 높은 성능을 가진 Set 구현체입니다. EnumSet의 모든 멤버들은 반드시 같은 enum type이어야 합니다.
출처
출처
반응형
'개발' 카테고리의 다른 글
도메인 주도 설계의 사실과 오해 (0) | 2024.04.29 |
---|---|
Getter 없이 Test해보기 (1) | 2023.11.24 |
매직넘버, 리터럴 어디까지 상수 처리해야 돼? (4) | 2023.11.06 |
1주 차 피드백을 2주 차 과제에 적용하기까지 (0) | 2023.11.01 |
원시 타입을 포장하자! (0) | 2023.10.31 |