天天看點

Objective-C入門(Learning Objective-C)

Objective-C是C語言的一個超集,也就是說,它支援基本的C語言的文法。

類的定義和實作是分别放在頭檔案和源檔案中的。頭檔案的擴充名是.h;源檔案是.m;還有一種.mm是用來放C++代碼的。

Classes(類)

Objective-C類的定義分為聲明和實作兩部分:

interface部分包含類的聲明,執行個體變量定義,以類相關的方法。interface通常都在.h檔案中;

代碼實作部分包含類方法的代碼,這部分放在.m檔案中。

下圖給出了類聲明的文法。

類MyClass繼承了基類NSObject。

類的聲明以@interface開始,後面跟着類名及繼承的基類;聲明以@end結束。

類的執行個體變量(或者叫成員變量)放在大括号中({ & });

類的方法在大括号外面聲明。

每行語句是以分号(;)來結尾的。

objective-c同時支援強類型和弱類型,強類型就不用說了,弱類型的話,是用“id”來聲明,用這個聲明的變量,什麼都能裝,大概就是這個意思。

Methods and Messaging(方法與消息)

Methods:

objective-c的類可以聲明兩種方法:類方法和執行個體方法。

執行個體方法就是隻有聲明執行個體後才能調用,聲明的時候用“-”;

類方法就像靜态方法一樣,直接用類就能調用,聲明的時候用“+”。

下圖為方法聲明文法:

Message:

叫這個message我總覺得怪怪的,怎麼翻譯都覺得别扭。算了,不糾結了,直接說吧。

調用一個方法的方式,就是發對象消息(messaging an object)。message就是方法簽名。所有發送給對象的message都是動态調用的,這也是objective-c實作多态的方法。

[myArray insertObject:anObject atIndex:0];

由上面的示例可以看到,一次調用,一個message是用一堆中括号([ & ])來包起來的。在中括号内,接收message的對象在左邊( myArray ),message在右邊( 也就是insterObject:anObject atIndex:0 )。

message也可以嵌套,比如參數可以是一個message,比如,message執行的結果可以傳給參數,或把message作為接收方,就行下面這行代碼一樣,這樣代碼也會比較簡潔。

[[myAppObject theArray] insertObject:[myAppObject objectToInsert] atIndex:0];

Objective-C用“.”操作符來操作通路方法( accessor methods ),用來擷取或設定對象狀态。通路方法的形式一般來說就是 :

-(type) prropertyName //讀取

-(void) setPropertyName:(type) //設定

下面是示例代碼:

//在消息中用“.”操作符調用通路方法[myAppObject.theArray insertObject:[myAppObject objectToInsert] atIndex:0];

//指派時的"."操作符調用通路方法

myAppObject.theArray = aNewArray;

類方法的實作示例:

@implementation MyClass

- (id)initWithString:(NSString *)aName

{

self = [super init];

if (self) {

name = [aName copy];

}

return self;

}

+ (MyClass *)createMyClassWithString: (NSString *)aName

{

return [[[self alloc] initWithString:aName] autorelease];

}

@end

note:在objective-C中 nil 相當于 null。比如:NSMutableArray *myArray = nill。

Declared Properties(屬性)

聲明屬性要比聲明通路方法簡單友善的多。

屬性的聲明是和方法的聲明放在一塊兒的,用“@property”來定義。

你一可以對屬性做一些設定,比如隻讀或是讀取時copy對象什麼的,如下:

@property BOOL flag;@property (copy) NSString *nameObject; // Copy the object during assignment.

@property (readonly) UIView *rootView; // Declare only a getter method.

每一個可讀的屬性,會自動設定一個同名的方法,用來讀取;

每一個可寫的屬性,會自動設定一個setPropertyName形式的方法,以set開頭,後面跟開頭字母大寫的屬性名。

在類的實作部分,你可以用“@synthesize”來訓示編譯器生成屬性相應的方法。

可以用兩種方式聲明:

@synthesize flag;@synthesize nameObject;

@synthesize rootView;

@synthesize flag, nameObject, rootView;

一般來說,屬性減少了很多代碼量。因為用通路方法實作的話,做的事情也差不多,而其還有寫一堆實作代碼。用@property來聲明,再用@synthesize在編譯的時候生成擷取及設定方法,明顯要簡單一些。

strings(字元串)

作為C的超集,它支援C風格的字元串。但一般來說不會用C風格的字元串。

字元串會作為類NSStrings的對象來傳送。

用類NSStrings來包裝字元串有很多好處,比如可以使用一些内建的方法來處理字元串,比如按長度排序,支援unicode,以及printf風格的格式化等等。

因為字元串經常被用到,是以,objective-c提供了一種簡寫方式來建立NSString對象。

如下所示(用@):

NSString *myString = @"My String\n";NSString *anotherString = [NSString stringWithFormat:@"%d %@", 1, @"String"];

// Create an Objective-C string from a C string

NSString *fromCString = [NSString stringWithCString:"A C string"

encoding:NSASCIIStringEncoding];

protocols(協定)

protocols按我的了解應該跟C#裡的接口差不多意思:

  • 可以被任何類實作;
  • 隻定義接口,沒有實作,沒有執行個體變量,實作部分交給繼承的類;
  • 常常用來指定委托對象的接口;
  • 聲明方式:

@interface MyClass : NSObject {}

@end

通過下面的代碼了解一下協定,委托及其他對象直接的關系: