2017-03-15 80 views
0

覆盖initialize()对于在类发送其第一条消息(设置UserDefaults等)之前执行代码很普遍。该文件指出,一个父类的实现可以被多次调用子类不重写initialize(),并给予上述做法的例子,以保护类器件执行代码不止一次如果initialize()多次调用:覆盖AppDelegate上的初始化 - 防止多次执行代码

的如果子类不实现initialize() - 运行时将调用继承的实现 - 或者如果子类显式调用[super initialize],则超类实现可能会被多次调用。如果你想保护自己免受多次运行,你可以在构造实现沿着这些线路:

+ (void)initialize { 
    if (self == [ClassName self]) { 
    // ... do the initialization ... 
    } 
} 

我重写我的AppDelegate initialize(),并试图避免多次运行有代码。类检查对我来说没有意义,因为检查self is AppDelegate.Type是否总是会评估为真(并在Xcode中给我一个警告)。

由于我们不是超类(AppDelegate的超类是UIResponder),类检查是否不适用?我的覆盖initialize()方法的内容只会运行一次,而不呼叫super或执行班级检查?

+0

我想如果你使用'==='而不是'is',它将不会为AppDelegate的子类返回true。 – dan

+0

@丹恩,我没有考虑过比较参考。这也是一个不错的选择,可以防止子类。您应该将其作为答案发布。 – JAL

+0

或'if self == AppDelegate.self'。但只要你不子类AppDelegate,你不需要检查。 –

回答

0

类检查的原因是因为您通常只想在initialize上运行代码(根据文档)。编写该条件可以保护您免受不执行initialize或致电[super initialize]的子类。下面是一个例子的类层次:

class Animal: NSObject { 
    class func initialize() { 
     //Some code I only want to run once 
    } 
} 


class Dog: Animal {} 

当我实例化一个新Dog,Objective-C的运行时间将initialize方法Dog的层次(超第一)发送到每类,所以Dog将接收消息,但将如此Animal。由于Dog未实现initialize,因此其超类将收到该消息,因此如果您未添加确保该消息是针对该类的检查,那么您的代码将最终执行两次。

doesn't really make sense in Swift,甚至可能更少在AppDelegate中如此,所以如果你想有代码只在斯威夫特运行一次,你应该使用延迟初始化的全局或静态的属性,如the migration docs定义。