2014年6月20日 星期五

[Objective-C]初學入門,以 Fraction為例


相關資訊:
Xcode版本:5.1.1
範例下載:GitHub

         歡迎加入 Objective-C的世界,此教學筆記將以實作分數為例簡單介紹這個語言。首先你必須先安裝好 Xcode,並且對 C語言有著基本的認識。接著,我們就開始一步步建置這個專案:

一、首先打開 Xcode,並從左上角的 File-->New-->Project新增一個專案。



二、由於我們並不是要寫 iOS的 App,所以從左下角的 OS X的類別選擇 Application,接著在右邊選擇 Command Line Tool (用命令提示字元來執行),然後 Next。


三、接著依照提示填上相關的專案名稱, Type選擇 Foundation。



四、Next之後你就可以選擇專案的儲存位置,以及下方問你有無需要作 Source Control, Source Control基本上是用來做版本控制的功能,由於我這邊並不需要,所以無需打勾。


五、Create後,就已經看到 Xcode幫我們產生的主程式以及相關的目錄。



六、按左上角的 Play按鈕,就可以在左下角見到預設產生的"Hello World"囉!這行訊息是使用 NSLog印出的,NSLog是 Objective-C用來在命令列印出訊息的函數,其中是以 NSString作為參數,若你想用 C語言的 printf也是可以的,但 NSLog預設提的格式訊息(如時間)是非常方便的,因此這邊均會使用 NSLog來印出訊息。



七、接著就要來實作 Fraction,直接對左邊的 testFraction目錄在觸控板上雙指按下(或點右鍵),選擇 New File。


八、選擇 OS X的 Cocoa --> Objective-C Class,然後 Next。



九、Class名稱我們這邊取名為 Fraction,Subclass of選擇 NSObject。NSObject是 Objective-C 的抽象根類別,幾乎所有的物件都繼承自它, NSObject可以幫你的物件初始化,並且真正實作它。



十、接下來你就可以看到它幫我們產生的兩個檔案 .h跟 .m檔。
  • .h 為標頭檔,所有要在外部使用的屬性及方法都要在這裡做宣告。
  • .m 為 Objective-C 的主檔,所有的屬性設定及方法都寫在這裡。





十一、接著我們直接看要寫的程式碼吧!

  • Fraction.h 在這裡我們要宣告外在類別可宣告外在可用的屬性(變數)與方法,若沒在此宣告,外在是無法順利呼叫的。

#import <foundation oundation.h="">

@interface Fraction : NSObject
//自行宣告屬性
@property (nonatomic)int numerator, denominator;
//宣告為property的主要功能是方便我們取用或設定物件裡的資料成員,會自動生成get, set方法
//nonatomic-->允許被不同執行緒同時存取,相對於atomic,速度較快,但較不安全
@property (nonatomic) NSString *str;

//手動實作 get、set方法
-(void) setTo:(int)n over:(int)d;
-(void) print;
-(Fraction*) add:(Fraction*) f;
-(Fraction*) Subtract:(Fraction*) f;
-(Fraction*) Multiply:(Fraction*) f;
-(Fraction*) Divide:(Fraction*) f;
-(Fraction*) Reduction:(Fraction*) f;
@end


  • Fraction.m

#import "Fraction.h"

@implementation Fraction
-(NSString*)description 
{
    //回傳一個NSString結果的分數
    return [NSString stringWithFormat:@"%d/%d",self.numerator,self.denominator];
}

-(NSString*) str
{
   //避免產生空物件
    if(!_str)
    {
        _str=[NSString new ];
    }
    return _str;
}

//覆寫Denominator的set方法,避免Denominator為0
-(void)setDenominator:(int)denominator 
{
    if(denominator) _denominator=denominator;
}

//設定分數之分子分母
-(void) setTo:(int)n over:(int)d 
{
    //兩種寫法均可行
    [self setNumerator:n];
    self.denominator=d;
}

-(void) print
{
    NSLog(@"%i / %i",self.numerator,self.denominator);
}

-(Fraction*) add:(Fraction*) f
{
    Fraction *sum=[Fraction new];
    sum.denominator = self.denominator * f.denominator;
    sum.numerator = self.numerator * f.denominator + self.denominator * f.numerator;
    sum=[sum Reduction:sum];
    return sum;
}

-(Fraction*) Subtract:(Fraction*) f
{
    Fraction *sub=[Fraction new];
    sub.denominator = self.denominator * f.denominator;
    sub.numerator = self.numerator * f.denominator - self.denominator * f.numerator;
    sub=[sub Reduction:sub];
    return sub;
}

-(Fraction*) Multiply:(Fraction*) f
{
    Fraction *mul=[Fraction new];
    mul.denominator = self.denominator * f.denominator;
    mul.numerator = self.numerator * f.numerator;
    mul=[mul Reduction:mul];
    return mul;
}

-(Fraction*) Divide:(Fraction*) f
{
    Fraction *div=[Fraction new];
    div.denominator = self.denominator * f.numerator;
    div.numerator = self.numerator * f.denominator;
    div=[div Reduction:div];
    return div;
}

-(Fraction*) Reduction:(Fraction*) f
{
    for (int i=2; i<f.denominator; i++) {
        while ((f.numerator%i==0) && (f.denominator%i==0)) {
            f.numerator = f.numerator / i;
            f.denominator = f.denominator / i;
        }
    }
    return f;
}



  • main.m 程式進入點,從這裡對 Fraction類別進行測試

#import <Foundation/Foundation.h>
//外部的 import是使用 ” 符號
#import "Fraction.h"

int main(int argc, const char * argv[])
{

    @autoreleasepool {
        Fraction *myFrac1;
        //myFrac1 = [Fraction alloc];
        //myFrac1 = [myFrac1 init];
        myFrac1 = [[Fraction alloc] init];
        [myFrac1 setTo:2 over:3];
        [myFrac1 print];
        
        Fraction *myFrac2 = [Fraction new];
        [myFrac2 setTo:1 over:3];
        //覆寫set的方法 使得此變數不得為0
        [myFrac2 setDenominator:0];
        [myFrac2 print];
        Fraction *myFrac3;
        myFrac3 = [myFrac1 add:myFrac2];//加
        [myFrac3 print];
        myFrac3 = [myFrac1 Subtract:myFrac2];//減
        [myFrac3 print];
        myFrac3 = [myFrac1 Multiply:myFrac2];//乘
        [myFrac3 print];
        myFrac3 = [myFrac1 Divide:myFrac2];//除
        [myFrac3 print];
        
    }
    return 0;

}

十二、Demo

沒有留言:

張貼留言