assign: 简单赋值,不更改索引计数;对基础数据类型 (NSInteger)和C数据类型(int, float, double, char,等)
copy: 建立一个索引计数为1的对象,然后释放旧对象; 对NSString
retain:释放旧的对象,将旧对象的值赋予输入对象,再提高输入对象的索引计数为1; 对其他NSObject和其子类
具体解释:
Copy其实是建立了一个相同的对象,而retain不是:
比如一个NSString对象,地址为0×1111,内容为@”STR”
Copy到另外一个NSString之 后,地址为0×2222,内容相同,新的对象retain为1, 旧有对象没有变化
retain到另外一个NSString之 后,地址相同(建立一个指针,指针拷贝),内容当然相同,这个对象的retain值+1
也就是说,retain是指针拷贝,copy是内容拷贝。在拷贝之前,都需要释放旧的对象。
assign/retain/copy具体的实现代码:
//get
-(MyObject*)myObject{
return _myObject;
}
// assign
-(void)setMyObject:(id)newValue{
_myObject = newValue;
}
// retain
-(void)setMyObject:(id)newValue{
if (_myObject != newValue) {
[_myObject release];
_myObject = [newValue retain];
}
}
// copy
-(void)setMyObject:(id)newValue{
if (_myObject != newValue) {
[_myObject release];
_myObject = [newValue copy];
}
}
在m文件中的使用方式:
在m文件中为一个property变量赋值:
间接赋值:
1.加self.
MyObject * aMyObject = [[MyObject alloc] init]; //aMyObject retainCount = 1;
self.myObject = aMyObject; //myObject retainCount = 2;
[aMyObject release];//myObject retainCount = 1;
2. 不加self.
MyObject * aMyObject = [[MyObject alloc] init]; //aMyObject retainCount = 1;
myObject = aMyObject; //myObject retainCount = 1;
[aMyObject release];//对象己经被释放
直接赋值:
3.加self.
self.myObject = [[MyObject alloc] init]; //myObject retainCount = 2;
4. 不加self.
myObject = [[MyObject alloc] init]; //myObject retainCount = 1;
readonly表示这个属性是只读的,就是只生成getter方法,不会生成setter方法.
readwrite设置可供访问级别
nonatomic非原子性访问,不加同步,多线程并发访问会提高性能。注意,如果不加此属性,则默认是两个访问方法都为原子型事务访问。
property
属性的操作:是为了为一个实例变量添加setter和getter方法
@property是一个预编译指令,用来自动声明属性的setter和getter方法。
@synthesize是一个预编译指令,表示在实现文件中创建该属性的setter和getter的代码
这里要注意一点(很重要):属性的名称不必与实例变量相等,但大多数情况下是一样的。
具体代码:
.h文件
#import <Foundation/Foundation.h>
@interface Student : NSObject{
NSString *_name; //定义了一个实例变量
}
@property (nonatomic, retain) NSString *name; //定义了一个property
@end
.m文件
#import "Student.h"
@implementation Student
@synthesize name = _name; // 这里使用name属性为_name变量添加setter和getter方法
- (void)dealloc
{
[_name release];
_name = nil;
[super dealloc];
}
@end