昨天介紹了OC中類的定義和使用:http://blog.csdn.net/jiangwei0910410003/article/details/41657603,今天咱們來繼續學習類的初始化方法和點語法的使用框架
1、首先來看一下類的初始化方法學習
在Java中咱們知道一個每一個類都有構造方法,這裏的初始化方法就是和構造方法一個概念的,可是這裏有一個區別是:Java中有默認構造方法,當咱們去自定義構造方法的時候,這個默認構造方法就會被替換了,可是OC中是不會的,這點須要注意。this
下面來看一下如何自定義初始化方法:spa
Person.h.net
// // Person.h // 03_InitDemo // // Created by jiangwei on 14-10-10. // Copyright (c) 2014年 jiangwei. All rights reserved. // #import <Foundation/Foundation.h> @interface Person : NSObject{ NSString *_name; NSInteger _age; } //自定義初始化方法,必須以init開頭 - (id)initWithName:(NSString *)name withAge:(NSInteger)age; //打印信息 - (void)showInfo; @end這裏咱們定義了一個初始化方法,對名稱和年齡進行初始化賦值操做
注:OC中自定義初始化方法的名稱必須是以init開頭code
在來看一下實現:對象
Person.mblog
// // Person.m // 03_InitDemo // // Created by jiangwei on 14-10-10. // Copyright (c) 2014年 jiangwei. All rights reserved. // #import "Person.h" @implementation Person - (id)initWithName:(NSString *)name withAge:(NSInteger)age{ //固定寫法,能夠背下來哦~~ //調用父類的初始化方法 self = [super init]; if(self != nil){ _name = name; _age = age; } return self; } - (void)test{ NSLog(@"test"); } - (void)showInfo{ [self test];//調用本身的方法 NSLog(@"name is %@ and age is %d",_name,_age); } @end這裏咱們看到了,初始化方法返回的類型是id類型,關於OC中的 id類型,能夠認爲和C語言中的void*是相等的,這種類型在OC中常常被用到,還有就是 self關鍵字的使用,這裏的self關鍵字就至關於Java中的this關鍵字,指代當前類對象,還有super關鍵字,這個和Java中的 super也是同樣的,指代父類對象。還有一個是 nil,他就至關於Java中的 null,空對象的概念,用於判斷的。
同時這裏還要記住一點:ip
之後OC中自定義初始化的方法的模板:開發
//固定寫法,能夠背下來哦~~ //調用父類的初始化方法 self = [super init]; if(self != nil){ _name = name; _age = age; } return self;這個沒什麼好說的,就是一個模板,因此初學者就背下來吧,不過用多了,天然就記住了。
下面來看一下如何使用初始化方法:
main.m
// // main.m // 03_InitDemo // // Created by jiangwei on 14-10-10. // Copyright (c) 2014年 jiangwei. All rights reserved. // #import <Foundation/Foundation.h> #import "Person.h" int main(int argc, const char * argv[]) { @autoreleasepool { //初始化方法只能調用一次 Person *person = [[Person alloc] initWithName:@"jiangwei" withAge:22]; [person showInfo]; person = [[Person alloc] init]; [person showInfo]; //id類型,相似於void* //可是id類型通常不這麼使用,通常會做爲方法的返回值和傳入的參數類型 id person1 = [[Person alloc] initWithName:@"huangdaoyang" withAge:23]; [person1 showInfo]; } return 0; }咱們使用了咱們自定義的方法實例化了一個Person對象出來,同時調用他的showInfo方法,打印結果,這裏咱們也會發現Person的init方法任然可使用,這個和Java中是有區別的,其實,在上篇文章中說到過,這個init方法是NSObject父類的,能夠猜測到這個方法的邏輯功能就是初始化,因此咱們在自定義初始化方法的時候,都是會用到這個方法的。固然咱們能夠定義多個初始化方法,後面咱們在介紹 Foundation框架的時候,會發現系統給我提供的類有不少自定義的初始化方法。
運行結果:
2、看一下OC中的點語法
OC中的點語法其實沒什麼高端的,可是他和Java中的那種使用對象變量直接訪問public類型的變量的點是不同的,因此這裏就單獨說明一下:
點語法只能適用於set/get方法,若是沒有對應的set/get方法的話,是不能使用.語法的
OC中的get方法和Java中不太同樣,OC中只要一個方法有返回值均可以認爲是get方法,Java中是形如getXXX這樣的才叫作get方法。
下面來看一個例子吧:
Person.h
// // Person.h // 04_UseDit // // Created by jiangwei on 14-10-11. // Copyright (c) 2014年 jiangwei. All rights reserved. // #import <Foundation/Foundation.h> @interface Person : NSObject{ //點語法只能適用於set/get方法,若是沒有對應的set/get方法的話,是不能使用.語法的 //這裏的get方法和其餘語言不同,只要有返回值就是get方法 NSString *_name; NSInteger _age; } - (void)setName:(NSString *)name; - (void)setAge:(NSInteger)age; - (NSString *)name; - (NSInteger) age; //這裏要注意,showInfo也是一個get方法 - (NSString *)showInfo; //只定義,不實現,因此在調用[person test]的時候,編譯時候不會報錯 //可是運行的時候就會報錯了,由於編譯的時候只會判斷方法有沒有定義,而運行的時候是須要判斷這個方法有沒有實現 - (void)test; @end在{}中定義了兩個屬性,注意都是如下劃線開頭的。而後在給這兩個屬性定義get/set方法,這樣咱們就可使用點語法來訪問這兩個屬性了。
同時這裏要注意的是其實showInfo方法也是一個get方法,由於他又一個返回值類型。
因此在OC中使用點語法有兩個條件:
一、必須是屬性
二、有對應的get/set方法
下面來看一下實現吧:
Person.m
// // Person.m // 04_UseDit // // Created by jiangwei on 14-10-11. // Copyright (c) 2014年 jiangwei. All rights reserved. // #import "Person.h" /** #import和#include的區別 1.當咱們在代碼中使用兩次#include的時候會報錯:由於#include至關於拷貝頭文件中的聲明內容,因此會報重複定義的錯誤 可是使用兩次#import的話,不會報錯,因此他能夠解決重複導入的問題,他會作一次判斷,若是已經導入一次就不導入了 */ @implementation Person - (void)setName:(NSString *)name{ _name = name; NSLog(@"setName is Execute"); } - (void)setAge:(NSInteger)age{ //這裏要注意,若是咱們定義的全局變量是age而不是_age的話 //這裏不能用age = age進行賦值 //可是也不能使用self.age = age,由於self.age等價於[self setAge:age]這樣就會出現死循環了 //因此咱們在定義全局變量的時候通常都會加上一個下劃線以便區分 _age = age; NSLog(@"setAge is Execute"); } - (NSString *)name{ NSLog(@"getName is Execute"); return _name; } - (NSInteger) age{ NSLog(@"getAge is Execute"); return _age; } - (NSString *)showInfo{ NSLog(@"showInfo is Execute"); return _name; } @end咱們看到了這裏對get/set方法的實現,看到上面的註釋:
咱們這裏不能使用self.age = age,由於self.age等價於[self setAge:age],這樣就會出現死循環了
這個和Java就有很大的區別了,Java中咱們是可使用this.age = age的,並且常常這樣作,可是OC中不行,緣由很簡單,由於OC中的點語法至關於調用set/get方法,那麼在set/get方法中調用set/get方法,那就會出現了死循環了。因此這點必定要注意。
還有一個須要注意的是,剛剛在Person.h中定義了一個test方法,可是在Person.m中並無實現,在OC中編譯是不會報錯的,可是運行的時候就會報錯了。
看一下如何使用點語法:
main.m
// // main.m // 04_UseDit // // Created by jiangwei on 14-10-11. // Copyright (c) 2014年 jiangwei. All rights reserved. // #import <Foundation/Foundation.h> #import "Person.h" int main(int argc, const char * argv[]) { @autoreleasepool { Person *person = [[Person alloc] init]; //此處的點語法調用的是set方法,等價於[person setName:@"jiangwei"]; person.name = @"jiangwei"; person.age = 22; //此處的點語法調用的get方法,等價於NSString *name = [person name]; NSString *name = person.name; NSLog(@"name is %@",name); name = person.showInfo; NSLog(@"name is %@",name); //調用test方法 [person test]; } return 0; }咱們這裏就可使用點語法進行賦值和取值操做了,其實等價於調用他們的get/set方法。
運行結果:
這裏須要注意的是報了一個錯誤,這個錯誤也是咱們後面開發過程當中常常犯的一個錯誤,就是這個方法沒有實現,咱們在Person.h中定義了test方法,可是沒有在Person.m中進行實現,在main.m中進行調用就報了這個錯誤,可是編譯的時候是沒有報錯的。
總結
今天就簡單的介紹了OC中的初始化方法的定義和點語法的使用,其中初始化方法相似於Java中的構造方法,點語法就是get/set的縮減版