我想初始化我的单例对象,该对象在我的应用程序中存储和管理整个类的应用程序设置。此外,应通过在启动时加载NSUserDefaults
的数据来初始化单例实例。但是,我不确定在发布时我应该在哪里初始化单例。
在Cocoa应用程序中,我首先在applicationWillFinishLaunching:
中编写单例初始化代码,从NSUserDefaults
获取参数。但是,后来我发现如果我在初始视图控制器中编写单例初始化代码(不带参数!),在故事板中设置,因为viewWillLoad:
,viewDidLoad:
等,这不能正常工作。视图控制器的类被称为之前 applicationWillFinishLaunching:
。
所以现在我确定我应该在<{strong> viewWillLoad:
之前的applicationWillFinishLaunching
中编写单例初始化代码,但仍然不确定它是否合适。具体来说,我知道NSApplicationMain
是第一个在启动时被调用的方法,但似乎下一个方法不是AppDelegate
内的任何方法,至少如果你使用故事板。
总结一下,我想问的是:
如果您使用情节提要,那么在NSApplicationMain
之后调用哪个类的方法。
我应该在应用中编写单例初始化代码?我想尽快初始化它。
iOS和OS X应用程序之间有区别吗?
答案 0 :(得分:3)
首次访问时应初始化它。这样的事情,也许是:
+ (instancetype)sharedInstance {
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
_instance = [[self alloc] init];
});
return _instance;
}
作为旁注,如果您只是将此类用作NSUserDefaults
的访问者,则可能需要考虑使用静态方法。
+ (id)mySpecificDataPoint {
return [[NSUserDefaults standardUserDefaults] objectForKey:@"whatever"];
}
+ (void)setMySpecificDataPoint:(id)data {
[[NSUserDefaults standardUserDefaults] setObject:data forKey:@"whatever"];
}
或者更精心设计的方法可能是为此目的向NSUserDefaults
添加类别。
@interface NSUserDefaults (MyData)
@property (nonatomic) NSString *someDataPoint;
@property (nonatomic) NSInteger somePrimitiveDataPoint;
@end
@implementation NSUserDefaults (MyData)
- (NSString *)someDataPoint {
return [self objectForKey:@"someDataPoint"];
}
- (void)setSomeDataPoint:(NSString *)someDataPoint {
[self setObject:someDataPoint forKey:@"someDataPoint"];
}
- (NSInteger)somePrimitiveDataPoint {
return [[self objectForKey:@"somePrimitiveDataPoint"] integerValue];
}
- (void)setSomePrimitiveDataPoint:(NSInteger)somePrimitiveDataPoint {
[self setObject:@(somePrimitiveDataPoint) forKey:@"somePrimitiveDataPoint"];
}
@end
答案 1 :(得分:2)
当你必须使用它时,你启动单例。所以Daji Djan说:懒得胜利。请注意,您不应该在applicationWillFinishLaunching
中进行长期处理,它应该尽快返回。
如果在applicationWillFinishLaunching期间单例不是必需的,你应该在第一个视图控制器的viewWillAppear中调用它,如果你需要尽快初始化它。
答案 2 :(得分:0)
如果你可以侥幸逃脱:尽可能晚了:)并且总是做所需的最低限度(但要尽可能保持你的代码干净!)