您的位置:首页 > 移动开发 > Objective-C

[转]objective-c 关于self的用法总结

2014-07-05 13:53 393 查看
创建一个Student类,继承NSObject类,代码:

1: #import

2:  

3: @interface Student : NSObject{

4:  

5: NSString *idd;

6: NSString *name;

7: }

8: @property (nonatomic, retain) NSString *idd;

9: @property (nonatomic, retain) NSString *name;

10:  

11: @end


.m文件 代码:

1: #import "Student.h"

2:  

3: @implementation Student

4: @synthesize idd,name;

5:  

6: - (void)dealloc

7: {

8: [idd release];

9: [name release];

10: [super dealloc];

11: }

12:  

13:  

14: @end


使用@propety @synthesize实现Student的成员属性的set
get方法。通常我们在其他类里访问Student的成员属性的做法:

获取student的名字通过student.name,给名字赋值[student setName:@“jordy”]; 其中student是Student类对象,如果在Student类内部访问其成员属性使用[self
setName:@”jordy”], 访问使用self.name;

注意:上述的代码,由于wordpress的原因,代码中的字符会自动保存为中文格式。你在使用时记得改为英文格式。

在Student.h和Student.m文件,是我们习惯性的写法,但似乎还是不能解释什么加self和不加self的区别,请看下面代码,是另一种习惯性的写法,还以Student类为例:

.h文件 代码:

1: #import

2:  

3: @interface Student : NSObject{

4:  

5: NSString *_idd;

6: NSString *_name;

7: }

8: @property (nonatomic, retain) NSString *idd;

9: @property (nonatomic, retain) NSString *name;

10:  

11: @end


.m文件 代码:

1: #import "Student.h"

2:  

3: @implementation Student

4: @synthesize idd = _idd;

5: @synthesize name = _name;

6:  

7: - (void)dealloc

8: {

9: [_idd release];

10: _idd = nil;

11: [_name release];

12: _name = nil;

13: [super dealloc];

14: }

15:  

16:  

17: @end


 

可以注意到上述代码,与之前的代码,在.h文件name变量改写为了_name;在.m文件中@sythesize的写法也发生了变化。

如果通过方法self._name获取属性的值,xcode编译器会提示错误,其实这也就说明了,我们通常使用self.name实际使用的是student类name的get方法,同理name的set方法亦是如此。

接下来从内存管理来说明使用self.和不使用self的区别:

ViewController.h文件,使用Student类,代码如下:

1: #import

2: @class Student;

3:  

4: @interface ViewController : UIViewController{

5:

6: St
b65a
udent *_student;

7: }

8:  

9: @property (nonatomic, retain) Student *student;

10:  

11: @end


ViewController.m文件,代码:

1: #import "ViewController.h"

2: #import "Student.h"

3:  

4: @implementation ViewController

5: @synthesize student = _student;

6:  

7: - (void)didReceiveMemoryWarning

8: {

9: [super didReceiveMemoryWarning];

10: }

11:  

12: #pragma mark - View lifecycle

13:  

14: - (void)viewDidLoad

15: {

16: [super viewDidLoad];

17: }

18:  

19: - (void) dealloc

20: {

21: [_student release];

22: _student = nil;

23: [super dealloc];

24: }


其它的方法没有使用到,所以这里就不在显示了。

在ViewController.m的viewDidLoad方法中创建一个Student类的对象

1: Student *mystudent = [[Student alloc] init];

2: self.student = mystudent;

3: [mystudent release];


这是相信有人会有疑问了,问什么创建student对象要这么复杂,似乎直接使用self.student = [[Student alloc] init]; 也没有问题,不加self有时也是挺正常的呀?

接下来就需要从内存角度来分析它们之间的区别了:

1、加self的方式:

Student *mystudent = [[Student alloc] init];       //mystudent 对象 retainCount = 1;

self.student = mystudent;   //student 对象 retainCount = 2;

[mystudent release];  //student 对象 retainCount = 1;

retainCount指对象引用计数,student的property 是retain 默认使用self.student引用计数+1。

2、不加self的方式

Student *mystudent = [[Student alloc] init];       //mystudent 对象 retainCount = 1;

student = mystudent;   //student 对象 retainCount = 1;

[mystudent release];   //student 对象内存已释放,如果调用,会有异常

3、加self直接赋值方式

self.student = [[Student alloc] init];  //student 对象 retainCount = 2;容易造成内存泄露

由于objective-c内存管理是根据引用计数处理的,当一个对象的引用计数为零时,gcc才会释放该内存。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: