제네릭 (Generic) 이란
클래스 내부에서 사용할 자료형을 나중에 인스턴스를 생성할 때 확정한다.
자료형의 객체들을 다루는 메서드나 클래스에서 컴파일 시간에 자료형을 검사해 적당한 자료형으로
선택할 수 있게 하기 위해 사용한다. 제네릭을 사용하면 객체의 자료형을 컴파일할 때 체크하기 때문에,
객체 자료형의 안전성을 높이고 형 변환의 번거로움이 줄어든다.
제네릭 사용방법
앵글브라켓(<>) 사이에 형식 매개변수를 넣어 선언한다. 이때 형식 매개변수는 하나 이상 지정 가능하다.
형식 매개변수는 자료형을 대표하는 용어로 T와 같이 특정 영문 대문자를 사용한다.
제네릭을 사용하면서 얻을 수 있는 장점은 의도하지 않은 자료형의 객체를 지정하는것을 막고
객체를 사용할 때 원래의 자료형에서 다른 자료형으로 형 변환시 발생할 수 있는 오류를 줄여준다.
간단한 제네릭의 예시
class Box<T>(t: T) { // 형식 매개변수로 받은 인자를 name에 저장
var name = t
}
fun main() {
val box1: Box<Int> = Box<Int>(1)
val box2: Box<String> = Box<String>("hello")
println(box1.name)
println(box2.name)
}
- 는 객체 box1, box2를 생성할 때 자료형이 결정된다.
- 생성자에서 유추할 수 있는 자료형이 있다면 이나 는 생략이 가능하다.
val box3 = box(1)
val box4 = box("Hello")
- 형식 매개변수 이름과 의미
제네릭 클래스
제네릭 클래스는 형식 매개변수 1개 이상을 받는다.
제네릭 클래스 내에 메서드에도 형식 매개변수를 사용할 수 있다.
주 생성자나 부 생성자에 형식 매개변수를 지정해 사용할 수 있다.
class Myclass<T> {
fun myMethod(a: T) {
...
}
}
class Myclass<T>(val myProp: T) {}
class Myclass<T> {
val myProp: T
constructor(myProp: T) {
this.myProp = myProp
}
}
그러면 다음과 같이 객체 인스턴스를 생성할 때 명시적으로 자료형을 지정할 수 있다.
var a = Myclass<Int>(12) // 주생성자 myProp에는 12가 할당되며 Int형으로 결정됨
println(a.myProp) // 12
println(a.javaClass) // Myclss