Initializers in Swift Class

深刻理解代替单纯记忆安全

  1. Swift初始化时会想尽一切办法确保初始化的安全、完备bash

  2. 就两种初始化方法:designated initializerconvenience initializeride

  3. designated方法是指当前类完成初始化最基础的方法,它能知足全部stored property的初始化赋值ui

  4. 初始化方法中必须保证全部stored property都被赋上初始值。固然,optional的属性能够不用明显的写出,默认会赋值为nilspa

  5. Swift初始化方法,子类通常不会将父类的方法继承下来。为的就是,一旦能够继承的话,那咱们就能够用父类的方法初始化一个子类对象了,此时子类的对象的属性可能并不okcode

    class Food {
        var name: String
        init(name: String) {
            self.name = name
        }
    }
    class Noodle: Food {
        let width: CGFloat
        init(width: CGFloat) {
            self.width = width
            super.init(name: "Noodle")
        }
    }
    复制代码
  6. 固然,上面所说是指通常状况,有些状况下子类仍是会继承父类的方法的cdn

    • 就是子类没有自定义designated initializer时,哪怕并子类并无增长stored property的状况下,依然不能继承父类初始化方法。由于自定义initializer初始化方法中除了为stored property赋值,可能还有其余自定义操做,既然写了designated initializer方法,就说明可能有本身的实现,此时再继承了父类的实现就触发4中的问题了
    class Food {
        var name: String
        init(name: String) {
            self.name = name
        }
        convenience init() {
            self.init(name: "unknown")
        }
    }
    class Noodle: Food {
    }
    let var1 = Noodle()
    let var2 = Noodle(name: "noddle")
    复制代码
  7. 一个复杂点的例子对象

    • Food是父类,RecipeIngredient是子类
    • 子类自定义实现了一个designated initializer,又重写了一个父类的designated initializer同时用做convenience initializer
    • 该状况下,父类的convenience init()方法会自动继承到子类中,由于子类实现了全部的的父类的designated initializer,因此父类的convenience initializer自动继承下来仍然会保证初始化的完备性

  8. 接着上面的例子,再来一层blog

    • ShoppingListItem做为更子的类,因为引入的purchased属性有默认值,因此会自动继承父类的各类初始化方法,由于继承下来不会影响初始化的完备性

简单总结

仍是那句话,为了确保初始化的完备性,能继承下去的就继承,一旦发现有影响完备性的漏洞,就不容许继承继承

  • convenience initializer只能访问本类的初始化方法为此目的
  • designated initializer只能执行父类的designated initializer也是如此
  • 全部规则都是如此;不记规则,只看原则

疑问

  1. 一方面Swift的子类不能继承父类的初始化方法,另外一方面,子类在重写父类的初始化方法时却仍要写上override,这点不是很理解
    • 若是不能继承父类初始化方法,那子类实现和父类一致的初始化方法时照理应该理解为定义了一个全新的初始化方法,而非真的重写了