我的单例访问方法通常是一些变种:
static MyClass *gInstance = NULL;
+ (MyClass *)instance
{
@synchronized(self)
{
if (gInstance == NULL)
gInstance = [[self alloc] init];
}
return(gInstance);
}
我能做些什么来改善这一点呢?
我的单例访问方法通常是一些变种:
static MyClass *gInstance = NULL;
+ (MyClass *)instance
{
@synchronized(self)
{
if (gInstance == NULL)
gInstance = [[self alloc] init];
}
return(gInstance);
}
我能做些什么来改善这一点呢?
当前回答
根据我下面的另一个回答,我认为你应该这样做:
+ (id)sharedFoo
{
static dispatch_once_t once;
static MyFoo *sharedFoo;
dispatch_once(&once, ^ { sharedFoo = [[self alloc] init]; });
return sharedFoo;
}
其他回答
根据我下面的另一个回答,我认为你应该这样做:
+ (id)sharedFoo
{
static dispatch_once_t once;
static MyFoo *sharedFoo;
dispatch_once(&once, ^ { sharedFoo = [[self alloc] init]; });
return sharedFoo;
}
关于单例宏代码的详细解释在Cocoa With Love博客上
http://cocoawithlove.com/2008/11/singletons-appdelegates-and-top-level.html。
KLSingleton是: 可子类化(到n阶) 弧相容 使用alloc和init是安全的 装载 线程安全的 无锁(使用+initialize,而不是@synchronize) Macro-free Swizzle-free 简单的
克林格尔顿
简单回答:太棒了。
长话短说:类似....
static SomeSingleton *instance = NULL;
@implementation SomeSingleton
+ (id) instance {
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
if (instance == NULL){
instance = [[super allocWithZone:NULL] init];
}
});
return instance;
}
+ (id) allocWithZone:(NSZone *)paramZone {
return [[self instance] retain];
}
- (id) copyWithZone:(NSZone *)paramZone {
return self;
}
- (id) autorelease {
return self;
}
- (NSUInteger) retainCount {
return NSUIntegerMax;
}
- (id) retain {
return self;
}
@end
一定要阅读dispatch/once.h头文件以了解发生了什么。在这种情况下,标题注释比文档或手册页更适用。
公认的答案,虽然它编译,是不正确的。
+ (MySingleton*)sharedInstance
{
@synchronized(self) <-------- self does not exist at class scope
{
if (sharedInstance == nil)
sharedInstance = [[MySingleton alloc] init];
}
return sharedInstance;
}
根据苹果文档:
... 您可以采用类似的方法来同步相关类的类方法,使用class对象而不是self。
即使使用self工作,它不应该,这看起来像一个复制和粘贴错误对我来说。 类工厂方法的正确实现应该是:
+ (MySingleton*)getInstance
{
@synchronized([MySingleton class])
{
if (sharedInstance == nil)
sharedInstance = [[MySingleton alloc] init];
}
return sharedInstance;
}