@property 的使用
在物件導向設計方法中我們會使用封裝來保護類別成員(成員亦包含了attribute與method),我們通常會寫method來存取attribute,命名為getter與setter,以下示範objective C的getter setter作法:
A.h
#import <Foundation/Foundation.h> @interface A : NSObject { int attr; } -(int)attr; //習慣上objective C不會在getter寫上get, 而是直接使用attribute作為getter -(void)setAttr:(int)a; @end
A.m
#import "A.h" @implementation A - (int)attr { return self->attr; //原則上不加self也可以, 加了就可以跟method內的變數作區隔 } -(void)setAttr: (int) a { self->attr = a; } @end
當你使用以上的寫法作為getter與setter時,您在程式中使用實體物件時,就可以用”.”的方式來作存取, 方在 assignment的左邊代表setter, 在右邊代表getter,示範如下:
main.m
#import <Foundation/Foundation.h> #import "A.h" int main(int argc, const char * argv[]) { A *a = [A alloc]; [a.attr 30]; // assign 30 給這個物件的attribute printf("The attribute of A is %d", a.attr); //取出a.attr的值, 會印出The attribute of A is 30 [a release]; }
是不是每次都要用傳統的作法才能達成”.”的取用呢? 其實Objective C安排了一個比較簡單的作法,就是@property,那為甚麼要先介紹上面的做法呢?很簡單因為使用任何捷徑都應該先知道他的原理吧?知道了原理未來才不會在debug中苦哈哈。使用@property的寫法如下:
A.h
#import <Foundation/Foundation.h> @interface A : NSObject { int attr; } @property int attr; //這樣就會自動建立gettery與setter @end
A.m
#import "A.h" @implementation A @synthesize attr; // 舊版的xcode需要成雙寫property與synthesize,新版的只要寫property其實就可以了, //synthesize可以讓你改property的名字, 寫法是 @synthesize attr = ppp; (就改成ppp了) @end
main.m
#import <Foundation/Foundation.h> #import "A.h" int main(int argc, const char * argv[]) { A *a = [A alloc]; [a.attr 30]; // 一樣可以使用 printf("The attribute of A is %d", a.attr); //取出a.attr的值, 會印出The attribute of A is 30 [a release]; }
基本上使用@property 會自動作三件事情:
- 建立了 setPropertyName (setter)
- 建立了 propertyName (getter)
- 建立了 propertyName (attribute)
*這些method是可以被override的, 所以使用了@property後, 你也可以改寫成自己想用的方式。
@property的設定 //用來設定property的參數
讀寫控制
- readwrite (預設): 可以讀寫,setter和getter方法都會自動加入
- readonly: 只能讀, 只會加getter的方法
setter相關部分
- assign(預設): 用於只會和可量度的數值作用的情況, _abc = b;
- retain/strong 在指定時會呼叫物件的retain指令, 然後前一個數值會release掉
- copy: 在指定時會呼叫物件的copy指令, 然後前一個數值會release掉 (一定要實作NSCopy的Protocol, 否則會掛點)
atomicity (單一性)
- atomic (預設): 會讓屬性有執行緒安全(thread-safe)的特性
- nonatomic: synthesize的存取者會直接回傳數值