와일드카드와 관련된 제네릭(Generic) 개념을 포괄적으로 이해하려면, 제네릭의 기본 개념, 와일드카드의 종류, 그리고 Object 타입과의 관계를 알아야 합니다. 다음은 이러한 개념들을 포함한 설명입니다.
제네릭은 자바의 클래스나 메서드를 작성할 때 데이터 타입을 미리 지정하지 않고, 사용할 때 지정할 수 있도록 하는 기능입니다. 제네릭을 사용하면 타입 안정성을 높이고, 코드의 재사용성을 높일 수 있습니다.
// 제네릭 클래스 예시
class Box<T> {
private T item;
public void setItem(T item) {
this.item = item;
}
public T getItem() {
return item;
}
}
위 예시에서 T는 타입 파라미터로, Box 객체를 생성할 때 실제 타입을 지정합니다. 예를 들어, Box<String>, Box<Integer>처럼 사용할 수 있습니다.
와일드카드는 제네릭 타입의 파라미터를 유연하게 사용할 수 있도록 합니다. 와일드카드는 ? 기호로 표현되며, 세 가지 주요 형태가 있습니다.
<?>): 모든 타입을 허용합니다.<? extends T>): 특정 타입 T의 하위 타입만 허용합니다.<? super T>): 특정 타입 T의 상위 타입만 허용합니다.<?>)모든 타입을 허용합니다. 예를 들어, List<?>는 어떤 타입의 리스트든 다 받을 수 있습니다.
public void printList(List<?> list) {
for (Object elem : list) {
System.out.println(elem);
}
}
<? extends T>)특정 타입 T의 하위 타입만 허용합니다. 예를 들어, List<? extends Number>는 Number와 그 하위 타입 (Integer, Double 등)의 리스트를 받을 수 있습니다.
public double sumOfList(List<? extends Number> list) {
double sum = 0;
for (Number num : list) {
sum += num.doubleValue();
}
return sum;
}
<? super T>)특정 타입 T의 상위 타입만 허용합니다. 예를 들어, List<? super Integer>는 Integer와 그 상위 타입 (Number, Object 등)의 리스트를 받을 수 있습니다.
public void addNumbers(List<? super Integer> list) {
list.add(1);
list.add(2);
}
Object 타입은 자바에서 모든 클래스의 최상위 클래스입니다. 따라서 제네릭을 사용하지 않는 컬렉션은 Object 타입으로 모든 객체를 저장할 수 있습니다. 하지만 제네릭을 사용할 때는 타입 안정성을 위해 명시적으로 타입을 지정해야 합니다.
예를 들어, List<Object>는 모든 타입을 저장할 수 있지만, 제네릭의 타입 안정성을 잃게 됩니다.
List<Object> list = new ArrayList<>();
list.add("Hello");
list.add(1);
이와 달리, 제네릭을 사용하면 다음과 같이 타입을 명시적으로 지정할 수 있습니다.
List<String> list = new ArrayList<>();
list.add("Hello");
// list.add(1); // 컴파일 오류
제네릭 타입 파라미터가 명시되어 있는 경우, Object 타입을 사용하는 것이 불가능하거나 제한될 수 있습니다. 이는 타입 안정성을 유지하기 위해서입니다.
List<String> stringList = new ArrayList<>();
List<Object> objectList = stringList; // 컴파일 오류
public void process(List<Object> list) {
// ...
}
process(stringList); // 컴파일 오류
위 예시에서 List<String>을 List<Object>로 변환하거나, List<String>을 인자로 받는 메서드에 List<Object>를 전달하는 것은 불가능합니다. 이는 타입 안정성을 위해 허용되지 않습니다.
<?>, <? extends T>, <? super T>).이러한 개념들을 이해하면 제네릭과 와일드카드를 효과적으로 사용할 수 있습니다.