메서드도 제네릭으로 만들 수 있다 그리고 거기서도 로 타입은 지양하자
public static Set union(Set s1, Set s2) {
Set result = new HashSet(s1);
result.addAll(s2);
return result;
}
경고가 발생한다 Set의 자료형이 없기 때문이다 경고를 없애려면 이 메서드를 타입 안전하게 만들어야한다 이걸 해결하는 방법은 단순하게 제네릭 메서드면 충분하다
public static <E> Set<E> union(Set<E> s1, Set<E> s2) {
Set<E> result = new HashSet(s1);
result.addAll(s2);
return result;
}
때떄로 불변 객체를 여러 타입으로 활용할 수 있게 만들어야 할 때가 있다.(모르겠는데….)
예전부터 계속 말하지만 제네릭은 런타입에 타입 정보가Object로 소거된다 이로 인해 하나의 객체를 여러 타입으로 매개변수화할 수 있다 하지만 이렇게 하려면 타입 매개변수에 맞게 그 객체의 타입을 바꿔주는 정적 팩터리를 만들어줘야 한다 이걸 제네릭 싱글톤 패턴이라 한다
제네릭 싱글턴 사용
private static UnaryOperator<Object> IDENTITY_FN = (t) -> t;
@SuppressWarnings("unchecked")
public static <T> UnaryOperator<T> identityFunction() {
return (UnaryOperator<T>) IDENTITY_FN;
}
이렇게 하면 항등 함수를 담은 클래스가 타입별로 하나씩 만들 필요 없이 소거 방식을 사용하여 제네릭 싱글톤 하나로 해결되었다 IDENTITY_FN 을 UnaryOperator 로 형변환 하면 비검사 형변환 경고가 발생한다 UnaryOperator 는 UnaryOperator 가 아니기 떄문이다 그래서 @SuppressWarnings를 달아주었다
Collection의 요소중 가장 큰걸 반환하는 max메서드가 있다면 컬렉션에 담긴 모든 원소가 상호 비교가능해야한다 Comparable을 구현한 컬렉션에 대해서만 max를 사용할 수 있는데 이 부분을 반드시 명시해줘야 해서 E를 띡 쓰는거보다
public static <E extends Comparable<E>> E max(Collection<E> c) {
...
}
이렇게 “모든 타입E는 자신과 비교할 수 있다” 라는 뜻을 정확하게 표현하기 위해서 사용한다