ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • swift - Initializer and Deinitializer #2 (Class Initializer, Designated Initializer, Convenience Intializer)
    swift 2021. 1. 12. 15:40

    // Designated Intializer : 지정 생성자 (Initializer Delegate를 해야함)
    // - default init을 사용하거나 슈퍼 클래스에서 designated Init을 상속한게 아니면 최소한 하나의 designated Init이 필요함
    // - super 클래스의 designated init을 호출해야함
    
    // Convenience Intializer : 간편 생성자
    // - super 클래스의 designated init을 직접 호출할 수 없음
    // - 반드시 동일한 클래스의 init을 호출해서 최종적으로 designated init이 호출되도록 해야 함
    
    
    class Position {
        var x: Double
        var y: Double
        
        // 모든 속성을 초기화 해야한다. -> Designated Init
        init(x: Double, y: Double) {
            self.x = x
            self.y = y
        }
        
        // Convenience init -> 유틸적으로 사용함 (필요한 속성만 초기화 하고 클래스에 있는 다른 init을 호출해서 나머지 초기화를 진행한다.)
        convenience init(x: Double) {
            self.init(x: x, y: 0.0) // designated init 호출
        }
    }

    Initializer Inheritance

    // init 또한 서브 클래스로 상속된다.
    // 근데 조금 까다롭다.
    // 기본적으로 super class로 구현한 init은 subclass로 상속되지 앟는다.
    
    // 1. 서브 클래스의 모든 속성이 기본값으로 초기화 되어 있고 designated init을 직접 구현하지 않았다면 super class의 모든 deisgnated init이 상속된다.
    // 2. 서브 클래스가 모든 desiganted init을 상속받았거나 overriding 했다면 모든 convenience init이 상속된다.
    
    class Figure {
       var name: String
    
       init(name: String) {
          self.name = name
       }
    
       func draw() {
          print("draw \(name)")
       }
    
        convenience init() {
            self.init(name: "Unknown")
        }
    }
    
    class Rectangle: Figure {
        var width: Double = 0.0
        var height: Double = 0.0
        
        init(name: String, width: Double, height: Double) {
            // 문제
            // 1. 슈퍼클래스의 desiganted init을 호출하지 않고 있다.
            // 2. 상위 구현을 호출하기 전에 상속받은 name 속성에 접근하고 있다.
            // 보통은 현재 클래스에 정의된 속성만 init하고 나머지는 슈퍼 클래스에 맡긴다.
    //        self.name = name
    //        self.width = width
    //        self.height = height
            
            // 문제해결
            self.width = width
            self.height = height
            super.init(name: name)
        }
        
        override init(name: String) {
            width = 0
            height = 0
            super.init(name: name)
        }
        // override를 하지 않았음에도 에러가 발생하지 않는다.
        // convenience는 기본적으로 같은 클래스의 init을 호출한다.
        // super class의 init을 호출하는 것은 기본적을 불가능 -> overriding이라는 개념이 적용되지 않는다.
        convenience init() {
            self.init(name: "Unknown")
        }
    }

    댓글

Designed by Tistory.