浅析Objective-C内存管理

在Xcode4.2及之后的版本中已经引入了引入了ARC(Automatic Reference Counting)机制,程序编译时Xcode可以自动给你的代码添加内存释放代码。如果不使用arc机制就需要自己来进行内存管理了。

objective-c的内存管理机制使用的是引用计数器的原理。

当一个对象在创建之后它的引用计数器为1,当调用这个对象的alloc、retain、new、copy方法之后引用计数器自动在原来的基础上加1,当调用这个对象的release方法之后它的引用计数器减1,如果一个对象的引用计数器为0,则系统会自动调用这个对象的dealloc方法来销毁这个对象。

#import <Foundation/Foundation.h>
#import "HPPStudent.h"

int main(int argc, const char * argv[]) {
    @autoreleasepool {
        HPPStudent *stu1 = [[HPPStudent alloc] init];// 调用alloc方法,引入计数+1
        NSLog(@"引用计数为:%d",[stu1 retainCount]);// retainCount为1

        HPPStudent *stu2 = [stu1 retain];

        NSLog(@"引用计数为:%d",[stu1 retainCount]);// retainCount为2

        [stu1 release];

        NSLog(@"引用计数为:%d",[stu2 retainCount]);// retainCount为1

        [stu2 release];

    }
    return 0;
}

另外,怎么知道对象是否被释放呢?

对象释放的时候通常会调用dealloc方法

#import <Foundation/Foundation.h>

@interface HPPStudent : NSObject {
    NSString *name;
}

- (void) setName:(NSString *)_name;

- (NSString *)name;

@end
#import "HPPStudent.h"

@implementation HPPStudent

- (void)dealloc
{
    NSLog(@"%@ dealloc", name);
    [super dealloc];//注意最后一定要调用父类的dealloc方法(两个目的:一是父类可能有其他引用对象需要释放;二是:当前对象真正的释放操作是在super的dealloc中完成的)
}

- (void) setName:(NSString *)_name {
    if (_name != name) {//首先判断要赋值的变量和当前成员变量是不是同一个变量
        [name release];//释放之前的对象
        name = [_name retain];//赋值时重新retain
    }
}

- (NSString *)name {
    return name;
}

@end

属性参数@property和@synthesize

在上面的类的实现了,我们实现了getter和setter方法,实现了这个两个方法之后,我们就直接通过点运算符来访问对象并且进行对象的操作。

#import <Foundation/Foundation.h>
#import "HPPStudent.h"

int main(int argc, const char * argv[]) {
    @autoreleasepool {
        HPPStudent *stu1 = [[HPPStudent alloc] init];
        stu1.name = @"mirhunana"; //使用点运算符
    }
    return 0;
}

其实,使用@property就可以自动添加getter、setter的声明,这样我们就不需要自行实现了。

#import <Foundation/Foundation.h>

@interface HPPStudent : NSObject 

//当编译器遇到@property时,会自动展开成getter和setter的声明
@property (nonatomic,retain)NSString *name;

@end

@synthesize可以自动添加getter、setter的实现

#import "HPPStudent.h"

@implementation HPPStudent

@synthesize name;

- (void)dealloc
{
    NSLog(@"%@ dealloc", name);
    [super dealloc];//注意最后一定要调用父类的dealloc方法(两个目的:一是父类可能有其他引用对象需要释放;二是:当前对象真正的释放操作是在super的dealloc中完成的)
}

@end

这里使用@property和@synthesize的效果跟上面直接实现getter和setter的效果是相同的。

另外,我们可以看到,在声明中对属性也加了关键词进行修饰。

@property (nonatomic,retain)NSString *name;

对于属性或者变量的定义,我们可以使用关键词进行修饰。

有下面基类关键字:

这里写图片描述

@property的参数默认参数:(atomic,readwrite,assign)

assign,用于基本数据类型

-(void)setA:(int)a{
    _a=a;
}

retain,通常用于非字符串对象

-(void)setA:(Car *)a{
    if(_a!=a){
        [_a release];
        _a=[a retain];
    }
}

copy,通常用于字符串对象、block、NSArray、NSDictionary

-(void)setA:(NSString *)a{
    if(_a!=a){
        [_a release];
        _a=[a copy];
    }
}

自动释放池

自动释放池就是将自动内存释放使用@autoreleasepool关键字声明一个代码块,如果一个对象在初始化时调用了autorelase方法,那么当代码块执行完之后,在块中调用过autorelease方法的对象都会自动调用一次release方法。

#import <Foundation/Foundation.h>
#import "HPPStudent.h"

int main(int argc, const char * argv[]) {
    @autoreleasepool {
        HPPStudent *person= [[[HPPStudent alloc] init] autorelease];//调用了autorelease方法,在autoreleasepool块结束位置会自动该对象进行释放操作
        person.name = @"mirhuanan";

    }
    return 0;
}

参考文章:iOS开发系列—Objective-C之内存管理

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值