从 c++ 到 objective-c(15):内存管理(续二)

从 c++ 到 objective-c(15):内存管理(续二)

ID:11696045

大小:46.00 KB

页数:3页

时间:2018-07-13

从 c++ 到 objective-c(15):内存管理(续二)_第1页
从 c++ 到 objective-c(15):内存管理(续二)_第2页
从 c++ 到 objective-c(15):内存管理(续二)_第3页
资源描述:

《从 c++ 到 objective-c(15):内存管理(续二)》由会员上传分享,免费在线阅读,更多相关内容在行业资料-天天文库

1、从C++到Objective-C(15):内存管理(续二)作者: DevBean 日期:2011年03月31日发表评论 (3)查看评论Setters如果不对Objective-C的内存管理机制有深刻的理解,是很难写出争取的setter的。假设一个类有一个名为title的NSString类型的属性,我们希望通过setter设置其值。这个例子虽然简单,但已经表现出setter所带来的主要问题:参数如何使用?不同于C++,在Objective-C中,对象只能用指针引用,因此setter虽然只有一种原型,但是却可以有很多种实现:可以直接指定,可以使用retain指定,

2、或者使用copy。每一种实现都有特定的目的,需要考虑你set新的值之后,新值和旧值之间的关系(是否相互影响等)。另外,每一种实现都要求及时释放旧的资源,以避免内存泄露。直接指定(不完整的代码)外面传进来的对象仅仅使用引用,不带有retain。如果外部对象改变了,当前类也会知道。也就是说,如果外部对象被释放掉,而当前类在使用时没有检查是否为nil,那么当前类就会持有一个非法引用。-(void)setString:(NSString*)newString{...稍后解释内存方面的细节self->string=newString;//直接指定}使用retain指定(

3、不完整的代码)外部对象被引用,并且使用retain将其引用计数器加1。外部对象的改变对于当前类也是可见的,不过,外部对象不能被释放,因为当前类始终持有一个引用。-(void)setString:(NSString*)newString{...稍后解释内存方面的细节self->string=[newStringretain];//使用retain指定}复制(不完整的代码)外部对象实际没有被引用,使用的是其克隆。此时,外部对象的改变对于当前类是不可变的。也就是说,当前类持有的是这个对象的克隆,这个对象的生命周期不会比持有者更长。-(void)setString:(

4、NSString*)newString{...稍后解释内存方面的细节self->string=[newStringcopy];//克隆//使用NSCopying协议}为了补充完整这些代码,我们需要考虑这个对象在前一时刻的状态:每一种情形下,setter都需要释放掉旧的资源,然后建立新的。这些代码看起来比较麻烦。直接指定(完整代码)这是最简单的情况。旧的引用实际上被替换成了新的。-(void)setString:(NSString*)newString{//没有强链接,旧值被改变了self->string=newString;//直接指定}使用retain指定(

5、完整代码)在这种情况下,旧值需要被释放,除非旧值和新值是一样的。//------不正确的实现-------(void)setString:(NSString*)newString{self->string=[newStringretain];//错误!内存泄露,没有引用指向旧的“string”,因此再也无法释放} -(void)setString:(NSString*)newString{[self->stringrelease];self->string=[newStringretain];//错误!如果newString==string(这是可能的),//

6、newString引用是1,那么在[self->stringrelease]之后//使用newString就是非法的,因为此时对象已经被释放} -(void)setString:(NSString*)newString{if(self->string!=newString)[self->stringrelease];//正确:给nil发送release是安全的self->string=[newStringretain];//错误!应该在if里面//因为如果string==newString,//计数器不会被增加} //------正确的实现------//最佳

7、实践:C++程序员一般都会“改变前检查”-(void)setString:(NSString*)newString{//仅在必要时修改if(self->string!=newString){[self->stringrelease];//释放旧的self->string=[newStringretain];//retain新的}} //最佳实践:自动释放旧值-(void)setString:(NSString*)newString{[self->stringautorelease];//即使string==newString也没有关系,//因为release是

8、被推迟的self->string=[n

当前文档最多预览五页,下载文档查看全文

此文档下载收益归作者所有

当前文档最多预览五页,下载文档查看全文
温馨提示:
1. 部分包含数学公式或PPT动画的文件,查看预览时可能会显示错乱或异常,文件下载后无此问题,请放心下载。
2. 本文档由用户上传,版权归属用户,天天文库负责整理代发布。如果您对本文档版权有争议请及时联系客服。
3. 下载前请仔细阅读文档内容,确认文档内容符合您的需求后进行下载,若出现内容与标题不符可向本站投诉处理。
4. 下载文档时可能由于网络波动等原因无法下载或下载错误,付费完成后未能成功下载的用户请联系客服处理。