Effective Java 05 - item 28 -
in Programming Language on Java
배열보다는 리스트를 활용하라
배열과 리스트는 두 가지 차이가 있다.
첫 번째
배열은 Convariant
(공변)이다. 쉽게 말해 Sub가 Super의 하위 타입이라면 배열 Sub[]는 배열 Super[]의 하위 타입이 된다는 뜻이다.
반면 제네릭은 Invariant
하다.
즉 서로다른 두 타입을 갖는 컬렉션 List<Type1>
와 List<Type2>
는 엄밀히 다른 타입이다.
두 번째
배열은 reify(실체화)된다.
배열은 런타임에도 자신이 담기로 한 원소의 타입을 인지하고 확인한다.
그러나 제네릭 타입은 컴파일 타입 이후 타입이 제거된다. 즉 런타임에는 알 수없다는 뜻이다.
이러한 소거 기법은 제네릭이 지원되기 이전 레거시 코드와 제네릭 타입을 함께 사용할 수 있게 하기 위한 메커니즘이었다.
둘의 교착점
이러다보니 배열과 제네릭은 유연하게 어우러지지 못한다.
제네릭 배열을 만들 수 없는 이유는 Type Safe
하지 않기 때문이다.
배열은 런타임에도 타입 안전하지만, 컴파일 타임에는 그렇지 않다.
제네릭은 런타임에는 타입 세이프하지 않지만, 컴파일 타임에는 안전하다.
때문에 둘은 서로 다른 메커니즘을 갖고 있으므로 섞어 쓰기가 어려우니, 배열을 리스트로 치환하는 방식으로 사용하도록 하자.
Reference
이펙티브 자바 Effective Java 3/E
조슈아 블로크