加载中…
正文 字体大小:

为什么不要在init和dealloc函数中使用accessor

(2012-05-09 20:01:11)
标签:

objective-c

ios

杂谈

Apple在MaciOS中关于内存管理的开发文档中,有一节的题目为:“Don’t Use Accessor Methods in Initializer Methods and dealloc”,文中说:“The only places you shouldn’t use accessor methods to set an instance variable are in initializer methods and dealloc.”但是并没有解释为什么。

下面这则代码说明了一种可能会引起错误的情况:父类在init中使用了value的setter,而子类重写了value的setter,而子类的init中会首先调用父类的init,这样就会导致子类value的setter会先于子类自己的init代码调用,就有可能会出现问题。这则代码就会在_info初始化之前进行操作。

造成这个问题的原因有两个:一就是在init使用了setter;二是子类重写了setter,导致在父类init时就会调用子类重写的setter,万一重写的setter中进行了一些子类特有的操作就可能会出现问题。

实际上两个条件很难同时满足,但万一不小心满足就很难发现这个错误。不是说一定不能在init或dealloc中使用accessor(如果父类变量是private,子类只能使用accessor),而是在使用的时候一定要明白可能会导致的问题,不要死记各种规则,而要真正理解背后的原理。

#import <Foundation/Foundation.h>

@interface Parent NSObject

{

@protected

    int _value;

}

@property (nonatomic, assign) int value;

@end

@implementation Parent

@synthesize value = _value;

- (id)init {

    self = [super init];

    if (self) {

        // Initialize self.

        self.value 1;

    }

    return self;

}

@end

@interface Child Parent

{

    NSString *_info;

}

@end

@implementation Child

- (id)init {

    self = [super init];

    if (self) {

        // Initialize self.

        _info @"child";

    }

    return self;

}

- (void) setValue:(int)value

{

    _value = value;

    NSLog(@"%@"_info);

}

@end

int main(int argc, const char * argv[])

{

    @autoreleasepool {

        // insert code here…

        Child *child = [[Child allocinit];

        NSLog(@"%d", child.value);

        [child release];

    }

    return 0;

}

0

阅读 评论 收藏 转载 喜欢 打印举报
  • 评论加载中,请稍候...
发评论

    发评论

    以上网友发言只代表其个人观点,不代表新浪网的观点或立场。

      

    新浪BLOG意见反馈留言板 电话:4006900000 提示音后按1键(按当地市话标准计费) 欢迎批评指正

    新浪简介 | About Sina | 广告服务 | 联系我们 | 招聘信息 | 网站律师 | SINA English | 会员注册 | 产品答疑

    新浪公司 版权所有