您的位置:首页 > 产品设计 > UI/UE

set内存管理

2014-04-17 21:50 176 查看
set 方法的内存管理

如果你有个OC对象类型的成员变量,就必须管理这个成员变量的内存。比如有个Car *_car

一、计数器的基本操作

1> retain : +1

2> release :-1

3> retainCount : 获得计数器

二、set方法的内存管理

1> set方法的实现

- (void)setCar:(Car *)car

{

    if ( _car != car )                               //首先判断一下,传进来的车是不是新车

    {

        [_car release];                              // 旧车 release 一次;

        _car = [car retain];                         // 新车 retain  一次,

     }

}

2> dealloc方法的实现(不要直接调用dealloc)            

- (void)dealloc                                      

{

    [_car release];                                 

    [super dealloc];

}

-------------------------------------------------------------------------

看下面这个例子

void test()

{

    

    Person *p = [[Person alloc] init]; //  创建一个Person对象,p指向该对象 用p来操作,p的年龄为20;p的计数器为现在为1

    p.age = 20;                        

    

    Car *c1 = [[Car alloc] init];     //  创建一个Car对象,c1指向该对象 用c1来操作,车的速度是250;c1的计数器为1 

    c1.speed = 250;                

    p.car = c1;                       //调用p的 setCar 把c1给p   c1的计数器+1   现在变为2

    

    Car *c2 = [[Car alloc] init];     //创建一个Car对象,c2指向该对象 用c2来操作,车的速度是300;c1的计数器为1 

    c2.speed = 300;

    p.car = c2;                       //把c1换成了c2, 因为p的_cer指向了c2,说以c1的计数器得-1, c2的计数器就+1. 现在c1的计数器是1,c2的计数器是2

    

    [c2 release];                     // c2的计数器-1, 现在变为1

    [c1 release];                     // c1为计数器-1,变为0, c1释放, 执行dealloc

    [p release];                      // p计数器-1, P释放,执行dealloc 把p以前所拥有的c2的计数器-1, 释放p2;

}

运行结果是:

[1905:303] 速度为250的Car对象被回收回

[1905:303] 速度为300的Car对象被回收了

[1905:303] 20岁的Person对象被回收了

@implementation Person

- (void)setCar:(Car *)car

{

    if (car != _car)

    {

        

        [_car release];                // 对当前正在使用的车(旧车)做一次release

        

        

        _car = [car retain];          // 对新车做一次retain操作

    }

}

- (Car *)car

{

    return _car;

}

- (void)setAge:(int)age



    _age = age;                      // 基本数据类型不需要管理内存

}

- (int)age

{

    return _age;

}

- (void)dealloc

{                                       

    [_car release];                   //在人挂掉以后, 把它以前所拥有的车做一次[_release]

    

    NSLog(@"%d岁的Person对象被回收了", _age);

    

    [super dealloc];

}

@end

@implementation Car

- (void)setSpeed:(int)speed

{

    _speed = speed;

}

- (int)speed

{

    return _speed;

}

- (void)dealloc

{

    

    NSLog(@"速度为%d的Car对象被回收了", _speed);

    

    [super dealloc];

}

@end

--------------------------------------------------------------------------------------------------------------------------------

控制set方法的内存管理

retain : release旧值,retain新值(用于OC对象)

assign : 直接赋值,不做任何内存管理(默认,用于非OC对象类型)

copy   : release旧值,copy新值(一般用于NSString *)

 

控制需不需生成set方法

readwrite :同时生成set方法和get方法(默认)

readonly  :只会生成get方法

 

多线程管理

atomic    :性能低(默认)

nonatomic :性能高

 

控制set方法和get方法的名称

setter : 设置set方法的名称,一定有个冒号:

getter : 设置get方法的名称

@property参数

1> OC对象类型

@property (nonatomic, retain) 类名 *属性名;

@property (nonatomic, retain) Car *car;

@property (nonatomic, retain) id car;

// 被retain过的属性,必须在dealloc方法中release属性

- (void)dealloc

{

    [_car release];

    [super dealloc];

}

2> 非OC对象类型(int\float\enum\struct)

@property (nonatomic, assign) 类型名称 属性名;

@property (nonatomic, assign) int age;

四、autorelease

1.系统自带的方法中,如果不包含alloc、new、copy,那么这些方法返回的对象都是已经autorelease过的

[NSString stringWithFormat:....];

[NSDate date];

2.开发中经常写一些类方法快速创建一个autorelease的对象

* 创建对象的时候不要直接使用类名,用self

-----------------------------------------------------------------------------------------------------------------------

看下面的例子

int main()

{

    

    User *u = [[User alloc] init];          //   u 的计数器是1

    u.name = @"小明";

    

    User *u2 = [[User alloc] init];         //   u2的计数器是1

    u2.name = @"小花";

    

    

    Status *s = [[Status alloc] init];      //   s的计数器是1

    s.text = @"今天天气真好!";             

    s.user = u;                             //  s引用了u   u的计数器变为2

    

    Status *s2 = [[Status alloc] init];     //  s2的计数器是1

    s2.text = @"今天天气真的很好!";

    s2.retweetStatus = s;                   // s2引用了s    s的计数器变为2

    s2.user = u2;                           // s2引用了u2   u2的计数器2 

    

    [u2 release];                           // [u2 release] u2计数器变为1

    [u release];                            // [u release] u计数器变为1

    [s2 release];                           // [u2 release] s2变为0 ;s2引用过的 s.和u2 都减1:u2变为0  u2释放 

    [s release];                            // [s release] s变为0  :u变为0 

    return 0;

}

运行结果:

[3607:303] 用户被释放

[3607:303] 微博被释放

[3607:303] 用户被释放

[3607:303] 微博被释放

Program ended with exit code: 0

@interface Status : NSObject

@property (nonatomic, retain) NSString *text;

@property (nonatomic, retain) NSString *icon;

// 从1970-01-01 00:00:00 开始,一共度过了多少毫秒

@property (nonatomic, assign) long time;

//@property (nonatomic) time_t time;

@property (nonatomic, retain) User *user;

@property (nonatomic, retain) Status *retweetStatus;

@property (nonatomic, assign) int commentsCount;

@property (nonatomic, assign) int retweetsCount;

@end

@implementation Status

- (void)dealloc

{

    [_text release];

    [_user release];

    [_retweetStatus release];

    [_icon release];

    NSLog(@"微博被释放");

    [super dealloc];

}

@end

@implementation User

- (void)dealloc

{

    [_name release];

    [_account release];

    [_icon release];

    [_password release];

    [_phone release];

    NSLog(@"用户被释放");

    [super dealloc];

}

@end

----------------------------------------------------------------------------------------

@property (nonatomic, retain) 类名 *属性名;

-
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息