공부/이펙티브코틀린

아이템 21 - 일반적인 프로퍼티 패턴은 프로퍼티 위임으로 만들어라

띵커베르 2024. 6. 6. 21:59
728x90
  • 프로퍼티 위임을 사용하여, 다양한 조건에서 적용해보자.
  • 코틀린에서는 디자인 패턴 Delegate Pattern 을 쉽게 구현할 수 있다.
  • by lazy {}
  • 보일러플레이트 코드를 줄일 수 있다.

 

/**
 * 아래 코드를 보시면 인터페이스 IWindow, 클래스 TransparentWindow, UI가 있습니다.
 * 클래스들은 모두 IWindow 인터페이스를 상속받았습니다.
 * UI는 TransparentWindow 를 상속받지 않고, mWindow 를 클래스 내부에 갖고 있습니다.
 * 그리고 UI는 mWindow.getWidth()처럼 mWindow 의 함수를 호출해주고 있습니다.
 * 이 구조에서, UI 클래스는 TransparentWindow 의 기능을 내부 변수 mWindow 에 위임하였습니다.
 * 이 구조를 유지하기 위해 UI는 IWindow 의 인터페이스를 상속받았고 오버라이드 메소드 안에서
mWindow 의 메소드를 호출해주었습니다.
 * 여기서 형식적인 코드(boilerplate code)는 UI.getWidth()와 UI.getHeight()입니다.
 * 만약 IWindow 의 메소드가 20개라면, 20개에 대한 wrapper 메소드를 모두 작성해주어야 합니다.
 */
interface IWindow {
    fun getWidth(): Int
    fun getHeight(): Int
}

open class TransparentWindow : IWindow {
    override fun getWidth(): Int {
        return 100
    }

    override fun getHeight(): Int {
        return 150
    }
}

class UI(window: IWindow) : IWindow {
    val mWindow: IWindow = window

    override fun getWidth(): Int {
        return mWindow.getWidth()
    }

    override fun getHeight(): Int {
        return mWindow.getHeight()
    }
}


Delegate pattern 적용

fun main(args: Array<String>) {
    val window: IWindow = TransparentWindow()
    val ui = UI(window)
    println("Width : ${ui.getWidth()}, height: ${ui.getHeight()}")
}

interface IWindow {
    fun getWidth(): Int
    fun getHeight(): Int
}

open class TransparentWindow : IWindow {
    override fun getWidth(): Int {
        return 100
    }

    override fun getHeight(): Int {
        return 150
    }
}

class UI(window: IWindow) : IWindow by window
728x90