Я немного смущен этим фрагментом кода (представленным в руководстве CocoaFundamentals), который переопределяет некоторые из методов при создании экземпляра singleton.Пример запроса Apple Singleton?
static id sharedReactor = nil;
+(id)sharedInstance {
if(sharedReactor == nil) sharedReactor = [[super allocWithZone:NULL] init];
return sharedReactor;
}
.
+(id)allocWithZone:(NSZone *)zone {
return[[self sharedInstance] retain];
}
-(id)retain {
return self;
}
В коде, где одноточечно экземпляр создан метод + sharedInstance называет [супер allocWithZone: NILL] от суперкласса (в моем случае это NSObject) allocWithZone выше вызывается только, если вы пытаетесь использовать его для создания нового синглтона.
Я немного смущен, это использование сохранения, особенно видение, поскольку сохранение также переопределяется, чтобы вернуть себя. Может кто-нибудь объяснить это, это не могло быть написано:
+(id)allocWithZone:(NSZone *)zone {
return [self sharedInstance];
}
-(id)retain {
return self;
}
EDIT_001:
На основе замечаний и чтения различных сообщений в Интернете я решил пойти со следующим (смотри ниже) У меня есть выбранный для совместного использования одноэлементного подхода, где в случае необходимости у меня будет возможность создать второй или третий экземпляр. Также на этом этапе, поскольку я использую только одноэлемент для части модели MVC для простого приложения для iPhone, я решил оставить защиту потоков. Я знаю, что это важно, и по мере того, как я больше знаком с программированием на iPhone, я, скорее всего, буду использовать + инициализацию (имея в виду проблему подкласса, где она может быть вызвана дважды). Также я добавил dealloc, во-первых, чтобы зарегистрировать сообщение, если синглтон быть освобожденным, но и очищать вещи должным образом, если синглтон больше не требуется.
@interface SharedManager : NSObject
+(id)sharedInstance;
@end
@implementation SharedManager
static id myInstance = nil;
+(id)sharedInstance {
if(myInstance == nil) {
myInstance = [[self alloc] init];
}
return myInstance;
}
-(void)dealloc {
NSLog(@"_deal: %@", [self class]);
[super dealloc];
myInstance = nil;
}
@end
В ходе тестирования я обнаружил, что у меня был набор статической переменной всухую в dealloc или она сохраняет свой указатель на исходный объект. Первоначально я был немного смущен этим, так как я ожидал, что область действия static будет экземпляром, я думаю, что это класс, что имеет смысл.
веселит Гэри
Возможно, вы захотите обновить это, чтобы обсудить проблему безопасности потоков. У Майка Эша есть хорошая статья о том, что наряду с другими проблемами с одиночным ядром: http://www.mikeash.com/pyblog/friday-qa-2009-10-02-care-and-feeding-of-singletons.html – nall
Лучше: читатели должны проверить почту Майка Эша. Это чрезвычайно важно, как это расширить для обеспечения безопасности потоков. Проблемы защиты потоков в общих синглетах влияют только на первоначальное создание. Для меня очень редко встречается такая проблема с потоками из-за того, что я обычно обрабатываю потоки (в моем коде крайне маловероятно, что первое использование синглтона было бы на рабочем потоке). Тем не менее, у меня возникает соблазн использовать использование + инициализации Майка, потому что это так дешево для реализации, и я думаю, что проблема с слишком ранним началом в большинстве случаев маловероятна. –
@Rob это все еще не запрещает несколько экземпляров. Он только «запрещает» их по соглашению. Питер Хосей написал отличный пост о том, как более правильно реализовать синглтоны: http://boredzo.org/blog/archives/2009-06-17/doing-it-wrong –