一、property
合成存取器:
@property的格式:
@property (修飾列表) 變量類型 變量名;
Xcode4.4之前:
@property使編譯器自定生成set/get方法聲明。
@synthesize自動生成set/get方法的實現
@synthesize還會自動生成私有成員變量
Xcode4.4以後:
不用再寫@synthesize,編譯器通過@property就能給我們生成set/get方法的聲明和實現,默認生成成員變量:_propertyName
用@property生成的成員變量是私有的。
當我們想改變默認的成員變量名時,@synthesize age = newName;‘
如果子類想訪問父類的成員變量,
1、通過set/get方法
2、顯示的聲明成員變量
**進入正題**
首先聲明:
category和protocol可以添加方法
category 和 protocol中可以添加@property 關鍵字
二、關於protocol中的property
在protocol中添加property時,其實就是聲明了 getter 和 setter 方法,在實現這個protocol協議的類中,我們要自己手動添加實例變量,並且需要實現setter/getter方法
偽代碼:
main.m
Student *student = [[Student alloc] init]; student.name = @"彭爸爸"; NSLog(@"%@", student.name);
person.h
設置協議,與其中的property
// // Person.h // 類別 和 協議 // // Created by ma c on 16/5/19. // Copyright © 2016年 彭盛凇. All rights reserved. // #import <Foundation/Foundation.h> @protocol personDelegate <NSObject> @property (nonatomic, copy) NSString *name; @end @interface Person : NSObject @end
student.h
生成成員變量,_name
// // PersonSon.h // 類別 和 協議 // // Created by ma c on 16/5/19. // Copyright © 2016年 彭盛凇. All rights reserved. // #import <Foundation/Foundation.h> #import "Person.h" @interface Student : NSObject <personDelegate> { //***聲明成員變量*** NSString *_name; } @end
student.m
這裡寫了兩種方法,一種是自動實現setter/gerter,一種為手動setter/gerter
// // PersonSon.m // 類別 和 協議 // // Created by ma c on 16/5/19. // Copyright © 2016年 彭盛凇. All rights reserved. // #import "Student.h" @implementation Student //------------------自動----------------------// //@synthesize // //編譯器期間,讓編譯器自動生成getter/setter方法。 // //當有自定義的存或取方法時,自定義會屏蔽自動生成該方法 //自動生成setter/getter方法 //@synthesize name; //------------------手動----------------------// //@dynamic // //告訴編譯器,不自動生成getter/setter方法,避免編譯期間產生警告 // //然後由自己實現存取方法 //實現Person中定義的屬性name的set方法 - (void)setName:(NSString *)name { _name = name; } //實現Person中定義的屬性name的get方法 - (NSString *)name { return _name; } @end
打印Log日志為:
說明成功實現property的基本功能,並可以實現賦值與取值操作
三、category中的property
在category中添加property時, 在@implentation添加 getter 和 setter方法時, 由於category不能添加實例變量
1)使用臨時全局變量來替代成員變量
首先聲明:Person沒有name屬性
main.m
導入頭文件:
#import "Person+Extension.h"
Person *person = [[Person alloc] init]; person.name = @"peng"; NSLog(@"%@", person.name);
Person+Extension.h
// // Person+Extension.h // 類別 和 協議 // // Created by ma c on 16/5/19. // Copyright © 2016年 彭盛凇. All rights reserved. // #import "Person.h" @interface Person (Extension) @property (nonatomic, strong) NSString *name; @end
Person+Extension.m
// // Person+Extension.m // 類別 和 協議 // // Created by ma c on 16/5/19. // Copyright © 2016年 彭盛凇. All rights reserved. // #import "Person+Extension.h" #import <objc/runtime.h> //***臨時變量*** static NSString *_name; @implementation Person (Extension) - (void)setName:(NSString *)name { _name = name; } - (NSString *)name { return _name; } @end
2)使用runtime 關聯對象 實現成員變量
除了Person+Extension.m 其他與 第一種方法一致
runtime Person+Extension.m
@implementation Person (Extension) - (void)setName:(NSString *)name{ objc_setAssociatedObject(self,@selector(name),name,OBJC_ASSOCIATION_RETAIN_NONATOMIC); } - (NSString *)name{ NSString *n = objc_getAssociatedObject(self, @selector(name)); return n; }
兩種方式打印Log日志相同,同時為: