ObjectiveC(11)_对象所有权和dealloc的使用

对象所有权

对象所有权的持有,一般有以下几种方式:
1、初始化方法

  • NSString参数
- (id)initWithName:(NSString *)name
{
    self = [super init];
    if (self) {
        _name = [name copy]; // 设置对象所有权
    }
    return self;
}
  • 其他参数
- (id)initWithName:(id)name
{
    self = [super init];
    if (self) {
        _name = [name retain]; // 设置对象所有权
    }
    return self;
}

2、设置方法

  • 直接赋值
- (void)setCPU:(CPU *)cpu
{
	_cpu = cpu;
}
  • 直接保留对象,在dealloc中释放对象
- (void)setCPU:(CPU *)cpu
{
	_cpu = [cpu retain];
}
  • 释放旧对象,保留新对象,在dealloc中释放对象
- (void)setCPU:(CPU *)cpu
{
	if (_cpu != cpu) {
		[cpu release];
		_cpu = [cpu retain];
	}
}

dealloc定义

dealloc方法作用是当对象的引用计数为0时,系统会自动调用dealloc方法,回收内存,它的一般写法是:

- (void)dealloc
{
	[super dealloc];
}
或
- (void)dealloc
{
	[_obj release];
	[super dealloc];
}
  • 调用父类的dealloc方法,是因为子类的某些实例是继承自父类的,所以需要继承父类的dealloc方法来释放父类拥有的这些对象。
  • 调用顺序:一般当子类的对象释放完时,再释放父类的所拥有的实例。这一点与调用初始化方法的[super init],正好相反。

示例

1、示例描述

  • 设有一个交通工具类Vehicle
  • 创建一个小汽车Car类,并继承Vehicle
  • 小汽车拥有引擎类Engine
    2、代码
  • 创建Vehicle.h
#import <Foundation/Foundation.h>
@interface Vehicle : NSObject
{
    NSString *_name;
}
- (id)initWithName:(NSString *)name;
@end
  • 创建Vehicle.m
#import "Vehicle.h"
@implementation Vehicle
// 初始化交通工具名称name
- (id)initWithName:(NSString *)name
{
    self = [super init];
    if (self) {
        _name = [name copy]; // 设置对象所有权
    }
    return self;
}
// 重写dealloc方法
- (void)dealloc
{
    NSLog(@"Vehicle dealloc");
    [_name release]; // 释放当前的_name
    [super dealloc]; // 调用父类方法
}
@end
  • 创建Car.h
#import "Vehicle.h"
@class Engine;
@interface Car : Vehicle
{
    Engine *_engine; // 创建引擎对象
}
- (void)setEngine: (Engine *)engine;
@end
  • 创建Car.m
#import "Car.h"
#import "Engine.h"
@implementation Car
// 创建设置引擎方法
- (void)setEngine: (Engine *)engine
{
    if (_engine!=engine) { // 设置对象所有权,避免重复对象
        [_engine release]; // 释放旧的对象所有权
        _engine =  [engine retain]; // 保留新的对象所有权
    }
}
// 重写dealloc方法
-(void)dealloc
{
    NSLog(@"Car dealloc");
    [_engine release]; // 释放_engine
    [super dealloc];
}
@end
  • 创建Engine.h
#import "Vehicle.h"
@interface Engine : Vehicle
@end
  • 创建Engine.m
#import "Engine.h"
@implementation Engine
@end
  • main方法中调用
#import <Foundation/Foundation.h>
#import "Vehicle.h"
#import "Car.h"
#import "Engine.h"
int main(int argc, const char * argv[]) {
    @autoreleasepool {
        NSString *name = [NSString stringWithFormat:@"BMW"];
        Car *car = [[Car alloc] initWithName: name];// name的对象所有权交给了Car类
        [name release];// 释放name自己的引用计数
        Engine *engine = [[Engine alloc] init];
        [car setEngine:engine]; // Engine的引用计数+1,将Engine的对象所有权交给Car类,Car类负责释放
        [engine release];// 释放engine自己的引用计数
        NSLog(@"Car的引用计数%ld",[car retainCount]);// 引用计数为1
        [car release];// 释放的时候,引用计数为0,会调用Car的dealloc方法,然后释放持有的engine对象,然后再调用父类Vehicle的dealloc方法,释放name对象
    }
    return 0;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

ruiurrui

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值