首页 > 重写init方法后,属性声明后为什么不为nil?

重写init方法后,属性声明后为什么不为nil?

学习Objective-C中,一般getter方法均实用if(!_variable)判断,在getter 方法中实例化。
今天遇到了一个UNRECOGNIZED SELECTOR SENT TO INSTANCE 的错误。
排查了发现声明的属性,第一次判断!_varible即为NO,运行设置断点发现属性指针已经有值。

请解释一下这个现象?

- (PlayingCardDeck *)playingCardDeck {
    BOOL noInit =!_playingCardDeck;
    NSLog(@"此处noInit 为 NO");
       
    if (noInit) {
        NSLog(@"getter is going");
        _playingCardDeck = [[PlayingCardDeck alloc] init];
        
    }
    
    return _playingCardDeck;
}

- (Card *)testCard {
    BOOL noInit =!_testCard;
    NSLog(@"此处noInit 为 YES");

    if (noInit) {
        NSLog(@"getter is going");
        _testCard = [[Card alloc] init];
        
    }
    return _testCard;
}

PlayingCardDeck的init的代码,Card为默认。

@implementation PlayingCardDeck

- (instancetype)init {
    
    self = [super init];

    if (self) {
        for (NSString *suit in [PlayingCard validSuits]) {
            for (NSUInteger rank = 1; rank <= [PlayingCard maxRank]; rank++) {
                PlayingCard *card = [[PlayingCard alloc] init];
                card.rank = rank;
                card.suit = suit;
                [self addCard:card];
            }
        }
    }
    NSLog(@"init Finished");
    return self;
}
@end 

看样子你在看斯坦福的公开课,先给你加个油。

从你发出的代码来看,好像没什么问题。

再检查一下你其他部分的代码,重点看一下,在调用playingCardDeck这个属性的时候,是否 全部 用了self. playingCardDeck,而不是 _playingCardDeck。

这样重写属性getter的方式称作懒加载,好处是什么这里不多说,要注意的就是, 第一次调用这个属性的时候一定要使用self.xxx ,而不是 _xxx的方式。因为只有self.xxx才会调用getter方法。所以为了保险起见,最好除了本属性getter和setter,其他地方全部使用self.xxx的方式来调用。

【热门文章】
【热门文章】