【Swift】required和convenience关键字的理解和使用

swift中强化了designated 初始化方法的地位。在子类中也强制(显示或隐式的)调用 super 版本的 designated 初始化,所以无论怎样被初始化的对象总是可以完成完整的初始化的。

class ClassB: ClassA {
    let numB: Int
    override init(num: Int) {
        numB = num + 1 
        super.init(num: num)
    }
}

注意:在 init 里我们可以对 let 的实例常量进行赋值,这是初始化方法的重要特点。正常情况下 let 声明的值是不可变的,无法被赋值,这对构建线程安全的 API 十分有用。而 init 只可能被调用一次,所以在 init 里我们可以为不变量进行赋值,而不会引起任何线程安全的问题

required关键字

designated初始化方法是来保证该类对象能被完整初始化的,如果designated init方法有required修饰,就表示子类一定要实现该init方法。这样做的好处是可以保证依赖于某个 designated 初始化方法的 convenience 一直可以被使用。
即:required修饰init方法, 强制子类重写该方法。

class ClassBBB: ClassAAA {
    let numB: Int
    required init(num: Int) {
        numB = num + 1
        super.init(num: num)
    }
}

convenience关键字

和required一样的是,convenience也是用来修饰init方法的,作用是增加便捷的init方法。但是有几点需要注意:

  • convenience init方法必须调用本类中 的designated初始化方法完成初始化设置。

  • convenience的初始化方法不能被子类重写或者是从子类中以super的方式被调用

class ClassAA {
    let numA: Int
    init(num: Int) {
        numA = num
    }
    convenience init(bigNum: Bool) {
        self.init(num: bigNum ? 10000 : 1) // 所有的 convenience 初始化方法都必须调用同一个类中的 designated 初始化完成设置
    }
}

class ClassBB: ClassAA {
    let numB: Int
    override init(num: Int) {
        numB = num + 1
        super.init(num: num)
    }
}

只要在子类中实现重写了父类 convenience 方法所需要的 init 方法的话,我们在子类中就可以使用父类的 convenience 初始化方法了。

convenience 和 required关键字可以同时使用

同时使用这两个关键字,确保子类对其进行实现。

你可能感兴趣的:(【Swift】required和convenience关键字的理解和使用)