~~~~我的生活,我的点点滴滴!!
1、介绍:
Objective-C语言关键词,与@synthesize配对使用。xcode4.5以及以后的版本,@synthesize可以省略
下面以 Person 类为例:
在. h 文件中:
@interface Person : NSObject
{
NSString * _name;
NSString * _sex;
NSInteger _age;
}
@property NSString * name;
@property NSString * sex;
@property NSInteger age;
表示声明了三个属性: name,sex,age, 默认生成3个对应的 setter 和 getter 方法
在.m 文件中:
@implementation Person
@synthesize name = _name;
@synthesize sex = _sex;
@synthesize age = _age;
@end
表示实现3个 setter 和 getter 方法,其中 name = _name 表示说在 getter 和 setter 方法中操作的实力变量是_name,如果省略了_name,_age,_sex,
那么会在.h文件中生成同名的实例变量 name,sex,age(注意:这里并没有下划线),此时生成的setter和getter 方法所操作的实例变量是 name,sex,age,
所以_name,_sex,_age 并没有被操作。在 ios5.0后,@synthesize也可以省略不写,此时在.h 文件中只写@property 即可,编译器会自动生成相应的实例
变量,实例变量的名字是属性名称前加下划线。
2、格式:
声明property的语法为:
@property (参数1,参数2) 类型 名字;
如:
@property(nonatomic,retain) UIWindow *window;
其中参数主要分为三类:
读写属性: (readwrite/readonly)
setter语意:(assign/retain/copy)
原子性: (atomicity/nonatomic)
各参数意义如下:
readwrite 产生setter\getter方法
readonly 只产生简单的getter,没有setter。
assign 默认类型,setter方法直接赋值,而不进行retain操作
retain setter方法对参数进行release旧值,再retain新值。
copy setter方法进行Copy操作,与retain一样
nonatomic 禁止多线程,变量保护,提高性能
3、说明与使用
3.1、getter分析
1、@property(nonatomic,retain)test* thetest;
@property(nonatomic, copy)test* thetest;
等效于:
-(test*)thetest
{
return thetest;
}
2、@property(retain)test* thetest;
@property(copy)test* thetest;
等效于:
-(test*)thetest
{
[thetest retain];
return [thetest autorelease];
}
3.2、setter分析
1、@property(nonatomic,retain)test* thetest;
@property(retain)test* thetest;
等效于:
-(void)setThetest:(test *)newThetest
{
if (thetest!= newThetest)
{
[thetestrelease];
thetest= [newThetest retain];
}
}
2、@property(nonatomic,copy)test* thetest;
@property(copy)test* thetest;
等效于:
-(void)setThetest:(test *)newThetest
{
if (thetest!= newThetest)
{
[thetestrelease];
thetest= [newThetest copy];
}
}
上面通过代码介绍了实现原理,下面通过一些具体文字来更清楚的描述他们:
4、strong
strong关键字与retain关似,用了它,引用计数自动+1,用实例更能说明一切
@property (nonatomic, strong) NSString *string1;
@property (nonatomic, strong) NSString *string2;
有这样两个属性,
@synthesize string1;
@synthesize string2;
猜一下下面代码将输出什么结果?
self.string1 = @"String 1";
self.string2 = self.string1;
self.string1 = nil;
NSLog(@"String 2 = %@", self.string2);
结果是:String 2 = String 1
由于string2是strong定义的属性,所以引用计数+1,使得它们所指向的值都是@"String 1", 如果你对retain熟悉的话,这理解并不难,
这样看来其实strong与retain基本上完全一样,完全通用,apple doc上也说过。
下面请对应weak来作一下比较,就会更加明确点
5、weak
如果这样声明两个属性:
@property (nonatomic, strong) NSString *string1;
@property (nonatomic, weak) NSString *string2;
并定义
@synthesize string1;
@synthesize string2;
再来猜一下,下面输出是什么?
self.string1 = @"String 1";
self.string2 = self.string1;
self.string1 = nil;
NSLog(@"String 2 = %@", self.string2);
结果是:String 2 = null
分析一下,由于self.string1与self.string2指向同一地址,且string2没有retain内存地址,而 self.string1=nil释放了内存,所以string1为nil。
声明为weak的指针,指针指向的地址一旦被释放,这些指针都将被赋值为 nil。
weak型的指针变量仍然可以指向一个对象,但不属于对象的拥有者,执行下面的代码
__weak NSString *name = self.nameField.text;
6、assign:
用于非指针变量。用于 基础数据类型 (例如NSInteger)和C数据类型(int, float, double, char, 等),另外还有id
如:
@property (nonatomic, assign) int number;
@property (nonatomic, assign) id className;//id必须用assign
反正记住:前面不需要加 “*” 的就用assign吧
7、copy
它指出,在赋值时使用传入值的一份拷贝。拷贝工作由copy方法执行,此属性只对那些实行了NSCopying协议的对象类型有效。所以只需要注意strong、weak、assgin这三个关键属性就够了
总结:
1、不带指针的基础数据类型变量,直接用assgin
2、想一直保留且不想在赋值后被莫名其妙的释放的,用strong
3、只是用来存值,不和其他变量发生赋值关系的用weak