Object-c中的屬性和成員變量的關系詳解


很多人在初學移動開發的時候會對object-c中的合成存取方法感到疑惑,此處嘗試為看到本文有緣人答疑解惑,鄙人才疏學淺,難免有疏漏謬誤之處,熱烈歡迎諸位看官拍磚指點.

1.合成存取方法:

OC為增加開發效率,從2.0之后不需要程序員自己來寫成員變量的setter和getter方法,取而代之的是自動合成的setter和getter。

系統自動合成setter和getter需要2步:

  1. 在類interface部分用@propert指令定義屬性。
  2. 在實現部分用@synthesize指令聲明屬性。

屬性的定義:如果為某個類定義了一個成員變量並提供了相應地setter、getter方法,那么可稱為定義了一個屬性(property)。

使用@synthesize的語法格式如下:

@synthesize 屬性名 [=成員變量名];

如果@synthesize后沒有屬性,如果沒有指定成員變量名,成員變量默認與合成的getter方法同名。 這里需要注意的是,此行為可能導致莫名其妙的錯誤,請看代碼:

//接口部分
#import
<Foundation/Foundation.h> @interface setGet : NSObject @property (setter=setAge:) int age; @property NSString *name; @end

 

 

//實現部分
#import
"setGet.h" @implementation setGet @synthesize age,name; - (void) setAge:(int)age { NSLog(@"Call setter method!"); self.age=age; } @end

 

//主程序部分
#import
<Foundation/Foundation.h> #import "setGet.h" int main(int argc, const char * argv[]) { @autoreleasepool { setGet* test=[[setGet alloc] init]; test.age=80; NSLog(@"The age is:%d",test.age); } return 0; }

在以上測試代碼中,將會無限輸出:Call setter method!

具體原因不言自明,正因為沒有在@synthesize部分對屬性名指定成員變量名,導致了程序產生了遞歸。

只要在實現部分稍作改動,程序便正常輸出:

//實現部分修改
#import "setGet.h"

@implementation setGet
@synthesize age=whatever,name;
- (void) setAge:(int)age
{
    NSLog(@"Call setter method!");
    self->whatever=age;
    // or :whatever=age;
    
}
@end

不過OC規范一般是下划線開頭來定義成員變量:_age。

補充一句:

“.”的用法僅限於getter和setter方法,用於左值則調用setter方法,用於右值則調用getter方法(如主程序中的NSLog中算是右值)。

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM