Replies: 3 comments
-
아이템 제목 에서 effective java를 통한 학습 내용이 스프링을 이해하는데 있어서 중요한 지식이라는 것도 알게 되었구요. 정리 감사합니다. |
Beta Was this translation helpful? Give feedback.
-
타입 안전 이종 컨테이너... 😤 (한국어로 번역된 책을 다시 한국어로 번역해야하는 책이 있다
저도 스프링 개념 다시 정리 들어갈 때 감사합니다. |
Beta Was this translation helpful? Give feedback.
-
진짜 어려운 파트 맡으셔서 고생 많으셨습니다! |
Beta Was this translation helpful? Give feedback.
-
0. 들어가며
33번은
타입 안전 이종 컨테이너
에 대한 이야기를 하는 아이템입니다.이 단어를 하나 하나 분해하여 의미를 파악해보겠습니다.
이를 합쳐서 생각해보면 다음과 같습니다.
의미를 알았으니 더 자세한 내용은 아래에서 알아보겠습니다.
1. 타입 안전 이종 컨테이너(비한정적 타입 토큰)
먼저 책에서 타입 이종 컨테이너를 설명하기위해 제시한 코드를 살펴봤습니다.
이 코드에서 Map 의 Key 로
Class<?>
를 받는데요.이를 책에서는 타입 토큰 이라고 표현하고, 더 정확히는 '비한정적 타입 토큰'이라고 부를 수 있습니다.
저는 이 코드를 보고 가장 먼저 일급 컬렉션이 떠올랐습니다.
Favorites 클래스는 Map 을 감싼 일급 컬렉션이고, 타입(타입 토큰)이 key 가 되고 해당 인스턴스가 value 로 되어있는 형태입니다.
그런데 이 예제 코드를 보고 뭔가 익숙한 하나가 더 떠올랐는데요.
제가 익숙함을 느낀 그 대상은 스프링에서의 빈 컨테이너입니다.
1.1 스프링 빈 컨테이너
보통 스프링 빈을 자동 주입받아서 사용하지만, 아래의 예시처럼 가끔 ApplicationContext 를 통해 직접 가져오기도 합니다.
context.getBean
을 호출하면 대략 다음과 같은 클래스들을 타고 이동하며 bean 을 가져옵니다.(설명을 위해 아주 많은 부분을 생략하고 간소화한 그림이니 참고 부탁드립니다.)
여기서 A, B를 합치면 책에서 소개한 타입 이종 컨테이너 Favorites 예제와 같은 구조가 됩니다.
하지만 스프링에서 이렇게 두 단계로 한 이유중 하나는 bean 이름을 붙이는 기능을 지원하기 위함입니다.
1.2 Collectinos
이외에도 이를 활용한 사례들을 책에서 소개해주었습니다.
java.utils.Collections 의 checkedSet, checkedList, checkedMap 과 같은 메서드들을 인데요.
소스를 까보니 그냥 모든 작업에 typeCheck 작업이 들어가있는 구현체를 반환하는 메서드였습니다.
그래서 제네릭만 제대로 써도 필요없는것 아닌가 했는데, 조금 더 읽어보니 로 타입을 위한 기능이라고 합니다.
로 타입은 제네릭이 자바에 정착하기전에 생겼던 안티패턴이지만 하위호환성을 위해 지원하는 문법이라고 합니다.
(자세한 내용은 아이템 26. 로 타입은 사용하지 말라 참고)
2. 슈퍼 타입 토큰
그런데 앞에서 살펴본 형태의 타입 안전 이종 컨테이너는 제네릭 타입은 담지 못한다는 단점이 있습니다.
위 처럼 가령
List<String>
혹은Set<Integer>
타입을 key 로 할 수 없습니다.이를 해결할 수 있는 방법으로 슈퍼 타입 토큰이라는 개념을 소개했는데요.
이 내용은 설명이 너무 길어질 수 있어 슈퍼타입토큰(Super Type Token) 글을 참고하시는걸 강추드립니다.
(추가로 책에서는 닐 개프터의 글도 추천합니다.)
3. 한정적 타입 토큰
1번에서 살펴봤던 예제에서는 제네릭에 와일드카드만 사용되었는데요.
와일드카드 대신 한정적 타입을 선언하는 방법도 있습니다.
이 메서드는 객체에 해당 타입의 어노테이션이 달려있다면 그 어노테이션을 반환하고, 아니라면 null 을 반환합니다.
즉, 이는 타입 안전 이종 컨테이너인 것이죠.
3.1 Class 클래스의 asSubClass 메서드
만약 Class<?> 객체를 3번에서처럼 한정적 타입만 받는 메서드에 넘기려면 어떻게 해야할까요.
이런 형태도 가능하긴 하지만 비검사 형변환이기 때문에 컴파일시 경고가 발생합니다.
이렇게 한다면 컴파일 경고 없이 넘길 수 있습니다.
Beta Was this translation helpful? Give feedback.
All reactions