본문 바로가기

Kotlin

Kotlin - Deligation

Delegation(위임) 패턴은 상속의 대안으로 적합하다고 증명되었고, Kotlin 은 별다른 코드 필요없이 이를 지원한다.

아래 예에서 DerivedClass는 특정 객체를 위임 함으로서 BaseInterface를 구현할 수 있다. by 절을 이용해서  b가 DerivedClass 내부에 저장 되고 컴파일러는 BaseInterface의 모든 메소드를 b를 바라보는 방법으로 생성하게 된다.

interface  BaseInterface {
    fun print()
}

class BaseImpl(val x: Int) : BaseInterface {
    override fun print() { print(x) }
}

class DerivedClass(b: BaseInterface) : BaseInterface by b

fun main() {
    val b = BaseImpl(10)
    DerivedClass(b).print()
}

 

Overriding

DerivedClass 가 마치 BaseInterface를 구현하고 있다고 생각하고 override 키워드를 이용해서 overriding 할 수 있다.

이 경우 재정의한 멤버는 위임한 객체(b: BaseInterface)의 멤버에는 접근 할 수 없고 DerivedClass 의 멤버에만 접근 가능하다. (예제를 보자)

interface  BaseInterface {
    val message: String
    fun printMessage()
    fun printMessageLine()
    fun print()
}

class BaseImpl(val x: Int) : BaseInterface {
    override fun printMessage() { print(x) }
    override fun printMessageLine() { println(x) }

    override val message: String = "BaseImpl: x = $x"

    override fun print() {
        println(message)
    }
}

class DerivedClass(b: BaseInterface) : BaseInterface by b {
    override fun printMessage() {
        print("abc")
    }

    fun printMessage2() {
        printMessage()
    }

    override val message = "Message of DerivedClass"
}

fun main() {
    val b = BaseImpl(10)
    DerivedClass(b).printMessage() // abc
    println()
    DerivedClass(b).printMessageLine() // 10

    val derived = DerivedClass(b)
    derived.print() // BaseImpl: x = 10 - message 를 재 정의 했지만 b의 print 함수를 사용하므로 b의 message가 출력된다.
    println(derived.message) // Message of DerivedClass
}