자바에서 제네릭은 데이터의 타입을 일반화한다(generalize)는 것을 의미한다.
클래스나 메소드에서 사용할 내부 데이터 타입을 컴파일 시에 미리 지정하는 방법이다.
객체의 타입을 컴파일 시에 체크하기 때문에 객체의 안정성이 높아지고, 캐스팅이 용이하다는 장점을 가진다.
클래스 또는 인터페이스 이름 뒤에 <>부호가 붙고 사이에 타입 파라미터가 위치한다.
public class 클래스명<T> {...}
public interface 인터페이스명<T> {...}
제네릭은 'T'와 같은 타입 변수를 사용하여 타입을 제한한다.
이때 extends 키워드를 사용하면 타입변수에 특정 타입만을 사용하도록 제한할 수 있다.
class AnimalList <T extends LandAnimal> {...}
클래스의 타입변수에 제한을 걸어 놓으면 클래스 내부에서 사용된 모든 타입변수에 제한이 걸린다. 인터페이스를 구현할 경우에도 implements 키워드가 아닌 extends 키워드를 사용해야 한다.
interface WarmBlood {...}
...
class AnimalList <T extends WarmBlood> {...}
클래스와 인터페이스를 동시에 상속받고 구현할 경우에는 & 기호를 사용하면 된다.
class AnimalList <T extends LandAnimal & WarmBlood> {...}
와일드 카드는 이름에 제한을 두지 않음을 표현하는데 사용되는 기호를 의미한다.
자바의 제네릭에서는 ? 기호를 사용하여 와일드 카드를 사용할 수 있다.
<?> 타입변수에 모든 타입 사용 가능
<? extends T> T타입과 T타입을 상속받는 자손클래스 타입만 사용 가능
<? super T> T타입과 T타입이 상속받은 조상클래스만 사용 가능
제네릭 타입을 선언한 메소드를 제네릭 메소드라 한다. 제네릭 타입을 메소드에서 선언할 때는 접근제한자와 반환타입 사이에 선언한다.
public <T> 리턴타입 메소드명 (매개변수) { . . . }
타입 파라미터를 컴파일 타임에만 검사하고, 런타임 시에는 해당 타입 정보를 알 수 없게 하는 것을 말한다.