1. 지네릭 메서드란?
- 메서드의 선언부에 지네릭 타입이 선언된 메서드를 '지네릭 메서드' 라고 부른다.
- 앞서 했던 예제 메서드 Collections.sort() 또한 지네릭 메서드이다.
- 지네릭 클래스에 정의된 타입 매개변수와 지네릭 메서드에 정의된 타입 매개변수는 전혀
별개의 것이다.
- 아래의 코드를 통해 이해하자.
class FruitBox<T>{
...
static <T> void sort(List<T> list, Comparator<? super T> c){
...
}
}
( 위의 FruitBox의 <T>와 static <T>와는 문자만 같을 뿐 서로 다른 것이다. )
( sort()는 static 멤버인데, 원래는 변수에 지네릭을 쓸 경우 static을 줄 수 없다. )
( 그러나, 메서드에 지네릭 타입을 선언하고 사용하는 것은 가능하다. )
( 메서드에 선언된 지네릭 타입은 지역 변수를 선언한 것과 같다. )
( 이 타입 매개변수는 메서드 내에서만 사용할 것이기 때문에, static이건 아닌건 상관없다. )
- 앞서 사용했던 메서드 makeJuice()를 지네릭 메서드로 바꾸면 아래와 같다.
적용 전 | 적용 후 |
static Juice makeJuice(FruitBox<? extends Fruit> box){ String tmp = ""; for(Fruit f : box.getList()) tmp += f+" "; return new Juice(tmp); } |
static <T extends Fruit> Juice makeJuice(FruitBox<T> box){ String tmp = ""; for(Fruit f : box.getList()) tmp += f+" "; return new Juice(tmp); } |
( 위 지네릭 메서드를 호출하면 아래와 같다. )
FruitBox<Fruit> fruitBox = new FruitBox<Fruit>();
FruitBox<Apple> appleBox = new FruitBox<Apple>();
System.out.println(Juicer.<Fruit>makeJuice(fruitBox);
System.out.println(Juicer.<Apple>makeJuice(appleBox);
( 그러나 대부분의 경우 컴파일러가 타입을 추정할 수 있기 때문에 생략이 가능하다. 아래의 코드를 보자. )
System.out.println(Juicer.makeJuice(fruitBox);
System.out.println(Juicer.makeJuice(appleBox);
( 한 가지 주의할 점은 지네릭 메서드를 호출할 때, 대입된 타입을 생략할 수 없는 경우에는 참조변수나
클래스 이름을 생략할 수 없다는 것이다. 아래의 코드를 보자. )
System.out.println(<Fruit>makeJuice(fruitBox));
// 에러 발생
System.out.println(this.<Fruit>makeJuice(fruitBox));
System.out.println(Juicer.<Fruit>makeJuice(fruitBox));
// 위 두 코드 정상 컴파일
( 지네릭 메서드는 매개변수의 타입이 지네릭으로 인해 복잡할 경우에도 간단한게 써줄 수 있다. 아래의 코드를 보자. )
< 적용 전 >
public static void printAll(ArrayList<? extends Product> list, ArrayList<? extends Product> list2){
...
}
< 적용 후 >
public static <T extends Product> void printAll(ArrayList<T> list, ArrayList<T> list2){
...
}
( 마지막으로 아래의 예제 코드를 보자. )
public static <T extends Comparable<? super T>> void sort(List<T> list)
( 위와 같은 코드가 나오면, 일단 아래의 코드처럼 와일드 카드를 걷어내보자. )
public static <T extends Comparable<T>> void sort(List<T> list)
( 위 문장은 List<T>가 Comparable 인터페이스를 구현한 것이어야 한다는 뜻이다. )
( 예를 들어, Student가 T이고 Person의 자손이라면, <? super Student>는 Student, Person, Object 모두가
가능하다는 뜻이다. )
'자바 > 지네릭스' 카테고리의 다른 글
지네릭 타입의 형변환과 제거 (0) | 2022.05.16 |
---|---|
와일드 카드 (0) | 2022.05.12 |
지네릭스의 전반적 개념(2) (0) | 2022.05.11 |
지네릭스의 전반적 개념(1) (0) | 2022.05.11 |