为什么在每个getter中都没有使用惰性实例化

时间:2014-04-21 14:52:15

标签: ios objective-c

在stanford课程中,Paul Hegarty更喜欢使用懒惰的实例化。例如,他发表了

的私人声明
@property (strong, nonatomic) (NSArray *)cards

然后他使用getter执行初始化

- (NSArray *) cards
{
   if(!_cards) _cards = [[NSArray alloc]init]
   return _cards;
}

我很酷。我不知道的是,在另一个时候,保罗宣布公开诉讼是为了打一场比赛:

 @property (strong, nonatomic) NSString *suit;

但在实现中他没有执行这个懒惰的实例化。所以我不明白西装字符串的alloc init在哪里发生? (适合作为指向NSString的指针 - 应该在堆中占据一席之地的对象)

#import "PlayingCard.h"

@implementation PlayingCard
@synthesize suit = _suit;

- (void)setSuit:(NSString *)suit
{
    if ([@[@"♣︎", @"♠︎", @"♥︎", @"♦︎"]containsObject: suit]) {
        _suit = suit;
    }
}

- (NSString *)suit
{
    return _suit? _suit: @"?";
}
@end

3 个答案:

答案 0 :(得分:4)

该属性是公开的,因此他假设它将被设置在某个地方。设置此属性时,可以分配,初始化然后将其设置为播放卡实例,例如:

PlayingCard *playingCard = [PlayingCard new];
[playingCard setSuit:@"spade"];

如果属性是私有的,则使用延迟初始化(因此您无法在类之外初始化它),但是您不希望在类的 init 方法中初始化它。 / p>

答案 1 :(得分:3)

当您要求cards实例时,不需要其他信息(即没有必要的参数)。您只需实例化PlayingCard并将其返回。

另一方面,suit可能是四个选项之一,所以有人需要在某处设置。请注意,此问题实际上与延迟初始化无关。它更多地与suit期望使用用户参数化值初始化的事实有关。

延迟初始化是一种说法,“在我要求它之前不要创建这个对象的实例。”但是在suit的情况下,您不希望在用户提供字符串之前创建字符串。

答案 2 :(得分:0)

懒惰实例化不是灵丹妙药,但如果您不需要花费周期在您需要之前同时实例化ivar对象,则可以改善对象实例化和应用程序响应性。这个效果对于一个小的简单类来说并不算什么,但是如果你有一个大的集合或一组对象,那么一次完全设置它们会在一点上减慢速度。

公平地说,同样的打击可能会在以后发生。