2011-01-05 21 views
5

Bunun gibi bir Singleton'um var:Arabirim Oluşturucusunda Singleton Kullanılsın mı?

static Universe *instance; 

+ (Universe *)instance { return instance; } 

+ (void)initialize 
{ 
    static BOOL initialized = NO; 
    if(!initialized) 
    { 
     initialized = YES; 
     instance = [[Universe alloc] init]; 
    } 
} 

- (id) init 
{ 
    self = [super init]; 
    if (self != nil) { 
     self.showHistory = YES; 
    } 
    return self; 
} 

ancak şimdi bunu Interface Builder'dan başlatmak istediğimi anlıyorum. Xzx41

 if (instance) 
     return instance; 

gibi init yöntemini kesmeyi düşünüyordum, bu kötü bir fikir mi? IB'yi +initialize yönteminde önceden oluşturulan örneği almayı tercih ederim.

cevap

6

Bu yapılabilir. Buck ve Yachtman tarafından kakao tasarım desenleri'da bunun hakkında bir bölüm var. Senin durumunda

sen çizgisinde bir şey yapabilirsiniz: yükleme kodu daha sonra doğru [[Universe alloc] init] olan çağrı yoluyla singleton gelip alacak

static Universe *instance; 

+ (Universe *)instance { return instance; } 

+ (id)hiddenAlloc 
{ 
    return [super alloc]; 
} 

+ (id)alloc 
{ 
    return [[self instance] retain]; 
} 

+ (void)initialize 
{ 
    static BOOL initialized = NO; 
    if(!initialized) 
    { 
     initialized = YES; 
     instance = [[Universe hiddenAlloc] init]; 
    } 
} 

- (id)init 
{ 
    if(instance==nil) // allow only to be called once 
    { 
    // your normal initialization here 
    } 
    return self; 
} 

uçlu ve hala gibi kodunda instance kullanabilirsiniz önce.

kitap daha fazla ayrıntı vardır ve iyi ölçmek için copyWithZone ve mutableCopyWithZone girişimleri yakalamak için new ve allocWithZone (her ikisi de sadece return [self alloc]; gibi), artı hata raporlama koçanları uygulanması tavsiye etmektedir.

+1

Bunu yapmak için ne yaptım Orijinal olarak bir Kakao uygulamasında olan bazı ağ istemcisi kodunun eklenti sürümü. Bir iş arkadaşının bir eklenti içinde olmasını istedim, böylece singleton rotasına gittim, böylece sadece ağ istemcisinin gerçek bir örneği (dahili olarak) olurdu. – ExitToShell

+0

@invariant, soruyu sormuş olmamı ve sadece aptal olarak reddetmememi sağladığım için harika bir cevap. –

+2

'+ alloc',' [[instance]] 'i döndürmelidir, çünkü 'alloc', sahip olunan bir nesneyi döndürür. –

1

Sızıntı olacak. Bunu değiştirirseniz,

, ancak yine de bana biraz kokuyor. IB'de bekarlar için ne kullandığınızı merak ediyorum; Kodumdaki bu yapıdan kaçınacağımı sanıyorum.

+0

Merhaba Seamus, evet, kod, "Bu kodlayıcı, initWithCoder'den değiştirilen nesnelerin döndürülmesini gerektiriyor" nedeniyle işe yaramıyor. Zaten IB'de Dış Nesne'yi kullanıma sunacağım. Mesele şu ki, uygulamadaki tüm parçalara bir köprü olarak tek bir merkezi Tekton kullanıyorum ... böylece her parça tektonla kendini kaydediyor. Ama sonra düşündüm ki, neden bazılarını tellemediniz? –

+0

http://stackoverflow.com/questions/350861/what-bad-practice-do-you-do-and-why/350900#350900 –

+1

^^ bu itirafları sevinir :) –