首页 > 代码库 > 黑马程序员-@property,@synthesize使用细节和id
黑马程序员-@property,@synthesize使用细节和id
一、@property和@synthesize 关键字以及使用细节
这两个关键字是编译器的特性,帮助我们有效的减少不必要代码的书写。
1.@property可以自动生成某个成员变量的setter和getter方法声明
1 #import <Foundation/Foundation.h> 2 3 @interface Person : NSObject 4 { 5 int _age; 6 // int age; 7 int _height; 8 double _weight; 9 NSString *_name;10 }11 12 // @property:可以自动生成某个成员变量的setter和getter声明13 @property int age;14 //- (void)setAge:(int)age;15 //- (int)age;16 17 @property int height;18 //- (void)setHeight:(int)height;19 //- (int)height;20 21 - (void)test;22 23 @property double weight;24 25 @property NSString *name;26 27 @end
这里注意不可以写成@property int _age;这样写的话会默认声明: - (void)setAge:(int)_age;- (int)_age; 就无法调用p.age或者[p setAge:10];只能这样调用p._age;或者[p set_age:10];
而@synthesize可以自动生成某个成员变量的setter和getter方法
1 #import "Person.h" 2 3 @implementation Person 4 5 // @synthesize自动生成age的setter和getter实现,并且会访问_age这个成员变量 6 @synthesize age = _age; 7 8 @synthesize height = _height; 9 10 @synthesize weight = _weight, name = _name;11 12 @end
这里注意@synthesize age = _age;不可以写成@synthesize age = age;或者@synthesize age;这样写的话会自动访问age这个变量而不是_age这个成员变量(假设@interface中有声明age这个变量)
2.其实还有更简便的方法,@interface中去掉成员变量的声明。但是注意如果@interface中没有声明成员变量,那么会自动生成@private类型成员变量。如果想要成员变量为@protected类型的,方便子类访问,那么只能在@interfae中声明了。
1 #import <Foundation/Foundation.h> 2 3 @interface Car : NSObject 4 { 5 //int _speed; 6 //int _wheels; 7 } 8 @property int speed; 9 @property int wheels;10 11 //@property int speed, wheels;12 - (void)test;13 @end
1 #import "Car.h" 2 3 @implementation Car 4 //@synthesize speed = _speed, wheels = _wheels; 5 // 会访问_speed这个成员变量,如果不存在,就会自动生成@private类型的_speed变量 6 @synthesize speed = _speed; 7 @synthesize wheels = _wheels; 8 9 - (void)test10 {11 NSLog(@"速度=%d", _speed);12 }13 14 @end
3.在Xcode4.4以后,@proterty关键字会自动声明和实现成员变量的setter和getter方法,无需@synthesize关键字
1 #import <Foundation/Foundation.h>2 3 @interface Dog : NSObject4 @property int age;5 @end
1 #import "Dog.h"2 3 @implementation Dog4 5 @end
这里要注意几点:
1>如果手动实现了set方法,那么编译器就只生成get方法和成员变量;
2>如果手动实现了get方法,那么编译器就只生成set方法和成员变量;
3>如果set和get方法都是手动实现的,那么编译器将不会生成成员变量。
二、id
>万能指针,能够指向任何OC对象,相当于NSObject *
>id类型的定义:
1 typedef struct objc_object2 {3 Class isa;4 } *id;
>注意id后面不要加*
id p = [person new];
>局限性:调用一个不存在的方法,编译器会立马报错。
1 #import <Foundation/Foundation.h>2 3 @interface Person : NSObject4 @property int age;5 @property id obj;6 @end
1 #import "Person.h"2 3 @implementation Person4 5 @end
1 #import <Foundation/Foundation.h> 2 #import "Person.h" 3 4 void test(id d) 5 { 6 7 } 8 9 int main(int argc, const char * argv[])10 {11 12 @autoreleasepool {13 Person *p = [Person new];14 NSObject *o = [Person new];15 // id == NSObject *16 // 万能指针,能指向\操作任何OC对象17 id d = [Person new];18 19 [d setAge:10];20 // 可以传任何对象21 [d setObj:@"321423432"];22 23 NSLog(@"%d", [d age]);24 }25 return 0;26 }
黑马程序员-@property,@synthesize使用细节和id