2012-04-05 71 views
1

嗨,伙计们! 我正在看书“Objective-C编程”作者:Stephen Kochan。其实我已经读完了。但现在我回到了第13章 - “基础C语言特性”。阅读完章后,我做了所有的练习,但是我坚持其中的一个练习。问题是,现在我在我的项目中使用ARC,并且我写的代码给了我一个错误。 当我修复它,我得到不正确的输出。所以这里是我的馏分类别主要的代码。ARC in Objective-C

Fraction.h

#import <Foundation/Foundation.h> 

@interface Fraction : NSObject { 
    int numerator; 
    int denominator; 
} 

@property int numerator, denominator; 

-(void) print:(BOOL)reduceCheck; 
-(void) setNumerator:(int)numerator andDenominator:(int)denominator; 
-(double) convertToNum; 
-(Fraction *) add:(Fraction *)fraction; 
-(Fraction *) subtract:(Fraction *)fraction; 
-(Fraction *) multiply:(Fraction *)fraction; 
-(Fraction *) divide:(Fraction *)fraction; 
-(void) reduce; 
-(id)initWithNumerator:(int)numeratorValue andDenominator:(int)denominatorValue; 
-(void)printOut; 
-(id)init; 
+(Fraction *)allocFraction; 
+(int)objectCounter; 
+(int)methodAddInvokedCounter; 

@end 

Fraction.m

#import "Fraction.h" 

static int gObjectCounter; 

static int gMethodInvokedCounter; 

static int greatestCommonDivisor(int u, int v) { 
    int temp; 

    while(v != 0) { 
     temp = u % v; 
     u = v; 
     v = temp; 
    } 
    return u; 
} 

@implementation Fraction 

@synthesize numerator, denominator; 

-(void) print:(BOOL)reduceCheck { 
    Fraction *resultFraction = [[Fraction alloc] init]; 
    [resultFraction setNumerator:numerator andDenominator:denominator]; 
    if(reduceCheck) { 
     [resultFraction reduce]; 
     NSLog(@"The Fraction is %i/%i - It was reduced", resultFraction.numerator, resultFraction.denominator); 
    } 
    else 
     NSLog(@"The Fraction is %i/%i - It was not reduced", resultFraction.numerator, resultFraction.denominator); 

    if(resultFraction.denominator != 1) { 
     if(resultFraction.numerator > resultFraction.denominator) { 
      Fraction *FractionObject = [[Fraction alloc] init]; 
      [FractionObject setNumerator:(resultFraction.numerator % resultFraction.denominator) andDenominator: resultFraction.denominator]; 
      int FractionNumber = resultFraction.numerator/resultFraction.denominator; 
      NSLog(@"The Fraction is %i/%i. The whole number of fraction is %i", FractionObject.numerator, FractionObject.denominator, FractionNumber); 
     } 
     else 
      NSLog(@"The Fraction is %i/%i", resultFraction.numerator, resultFraction.denominator); 
    } 
    else 
     NSLog(@"The whole number of the Fraction is %i", resultFraction.numerator); 
} 

-(void) setNumerator:(int)value andDenominator:(int)value2 { 
    numerator = value; 
    denominator = value2; 
} 

-(double) convertToNum { 
    if(denominator != 0) 
     return (double)numerator/denominator; 
    else 
     return NAN; 
} 

-(Fraction *) add:(Fraction *)fraction { 
    //extern int gMethodInvokedCounter; 
    Fraction *FractionResult = [[Fraction alloc] init]; 
    FractionResult.numerator = numerator * fraction.denominator + denominator * fraction.numerator; 
    FractionResult.denominator = denominator * fraction.denominator; 
    [FractionResult reduce]; 
    gMethodInvokedCounter++; 
    return FractionResult; 
} 

-(Fraction *) subtract:(Fraction *)fraction { 
    Fraction *FractionResult = [[Fraction alloc] init]; 
    FractionResult.numerator = numerator * fraction.denominator - denominator * fraction.numerator; 
    FractionResult.denominator = denominator * fraction.denominator; 
    [FractionResult reduce]; 
    return FractionResult; 
} 

-(Fraction *) multiply:(Fraction *)fraction { 
    Fraction *FractionResult = [[Fraction alloc] init]; 
    FractionResult.numerator = numerator * fraction.numerator; 
    FractionResult.denominator = denominator * fraction.denominator; 
    [FractionResult reduce]; 
    return FractionResult; 
} 

-(Fraction *) divide:(Fraction *)fraction { 
    Fraction *FractionResult = [[Fraction alloc] init]; 
    FractionResult.numerator = numerator * fraction.denominator; 
    FractionResult.denominator = denominator * fraction.numerator; 
    [FractionResult reduce]; 
    return FractionResult; 
} 

-(void) reduce { 
    int u = numerator; 
    int v = denominator; 

    int greatestCommonDivisor(int u, int v); 

    greatestCommonDivisor(u, v); 

    numerator /= u; 
    denominator /= u; 
} 

-(id)initWithNumerator:(int)numeratorValue andDenominator:(int)denominatorValue { 
    self = [super init]; 

    if(self) 
     [self setNumerator:numeratorValue andDenominator:denominatorValue]; 

    return self; 
} 

-(void)printOut { 
    printf("%i/%i", numerator, denominator); 
} 

-(id)init { 
    return [self initWithNumerator:0 andDenominator:0]; 
} 

+(Fraction *)allocFraction { 
    //extern int gObjectCounter; 
    gObjectCounter++; 

    return [Fraction alloc]; 
} 

+(int)objectCounter { 
    //extern int gObjectCounter; 

    return gObjectCounter; 
} 

+(int)methodAddInvokedCounter { 
    return gMethodInvokedCounter; 
} 

@end 

的main.m

#import <Foundation/Foundation.h> 
#import "Fraction.h" 

Fraction *calculateFractions (Fraction **array, int numberOfElements) { 
    Fraction *resultFraction = [[Fraction alloc] initWithNumerator:array[0].numerator andDenominator:array[0].denominator]; 
    Fraction *holder; 

    for(int i = 1; i < numberOfElements; i++) { 
     holder = [resultFraction add:array[i]]; 
     resultFraction = holder; 
    } 

    return resultFraction; 
} 

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

    @autoreleasepool { 

     const int numberOfFractions = 5; 

     Fraction *fractionArrayElementOne = [[Fraction alloc] initWithNumerator:5 andDenominator:10]; 
     Fraction *fractionArrayElementTwo = [[Fraction alloc] initWithNumerator:8 andDenominator:13]; 
     Fraction *fractionArrayElementThree = [[Fraction alloc] initWithNumerator:7 andDenominator:15]; 
     Fraction *fractionArrayElementFour = [[Fraction alloc] initWithNumerator:9 andDenominator:23]; 
     Fraction *fractionArrayElementFive = [[Fraction alloc] initWithNumerator:4 andDenominator:17]; 

     Fraction __autoreleasing *arrayOfFractions[numberOfFractions]= {fractionArrayElementOne, fractionArrayElementTwo, fractionArrayElementThree, fractionArrayElementFour, fractionArrayElementFive}; 

     printf("Fraction Expression: %i/%i + %i/%i + %i/%i + %i/%i + %i/%i = ", arrayOfFractions[0].numerator, arrayOfFractions[0].denominator, arrayOfFractions[1].numerator, arrayOfFractions[1].denominator, arrayOfFractions[2].numerator, arrayOfFractions[2].denominator, arrayOfFractions[3].numerator, arrayOfFractions[3].denominator, arrayOfFractions[4].numerator, arrayOfFractions[4].denominator); 

     Fraction *calculateFractions (Fraction **array, int numberOfElements); 

     Fraction *resultOfFractionArrayCalculation; 

     resultOfFractionArrayCalculation = calculateFractions(arrayOfFractions, 5); 

     printf("%i/%i\n", resultOfFractionArrayCalculation.numerator, resultOfFractionArrayCalculation.denominator); 

    } 
    return 0; 
} 

输出
分数表达:5/10 + 8/13 7/15 + 9/23 + 4/17 + = 1/0

问:我做错了什么?

提前感谢!

+0

您是否也可以提供您编写的代码,然后您如何针对ARC进行更正? – Novarg 2012-04-05 09:02:16

+0

@Novarg我只是将函数的参数从“Fraction * array”设置为“Fraction **数组” fractionArrayElementFive};”。 – 2012-04-05 09:07:41

+0

@Novarg那么,你能帮我吗? – 2012-04-05 10:47:02

回答

1

Reduce方法中存在一个错误。你扔掉gcd的结果,只用分子把分子和分母分开。只要numerator > denominator您将以1/0作为分数。

另外,init应该将默认分母设置为1,而不是零。

+0

谢谢,我从来没有遇到过这个代码的问题。 – 2012-04-05 12:58:14

+0

好的,我明白了。这是因为我调用了一个函数,但返回的值没有被使用。再次感谢你。真的不错的错误。 – 2012-04-05 13:06:20