Reputation: 1536
I need to extend a Fraction class by adding couple of methods that conform to NSComparisonMethods protocol.
This is my code: Fraction.h
#import <Foundation/Foundation.h>
@protocol NSComparisonMethods
-(BOOL) isEqualTo:(id)object;
-(BOOL) isLessThanOrEqualTo:(id)object;
-(BOOL) isLessThan:(id)object;
-(BOOL) isGreaterThan:(id)object;
-(BOOL) isGreaterThanOrEqualTo:(id)object;
-(BOOL) isNotEqualTo:(id)object;
@end
@interface Fraction : NSObject <NSComparisonMethods>
@property int numerator, denumerator;
-(void) print: (BOOL) test;
-(void) setTo: (int) n over: (int) d;
-(double) convertToNum;
-(void) reduce;
-(id) addFrac:(id)f;
-(void) justPrint;
-(id) initWith:(int)n over:(int)f;
+(Fraction *) allocF;
+(int) count;
+(int) gCounter;
@end
Fraction.m
#import "Fraction.h"
@implementation Fraction
@synthesize numerator, denumerator;
-(BOOL) isEqualTo:(id)object
{
Fraction *selfCopy = [[Fraction alloc] init];
if (selfCopy == object)
return YES;
else
return NO;
}
//more methods..
main.m
#import <Foundation/Foundation.h>
#import "Fraction.h"
#import "Fraction+MathOperations.h"
int main (int argc, const char * argv[]) {
@autoreleasepool {
Fraction *fracA = [[Fraction alloc] init];
Fraction *fracB = [[Fraction alloc] init];
id Object;
[fracA setTo:1 over:4];
[fracB setTo:1 over:4];
Object = fracB;
NSLog(@"%s",[fracA isEqualTo: Object]? "Yes":"No");
}
return 0;
}
Isn't it suppose to work properly? Im getting No
no metter what..
Is the problem in the method implementation? cant I test object like this (selfCopy == object)
? should I do selfCopy.numerator
(exedra..)
Upvotes: 0
Views: 305
Reputation: 51
My version:
-(BOOL) isEqualTo: (Fraction *) f
{
Fraction *temp1 = [[Fraction alloc] init];
Fraction *temp2 = [[Fraction alloc] init];
[temp1 setTo:[self numerator] over:[self denominator]];
[temp2 setTo:[f numerator] over:[f denominator]];
[temp1 reduce];
[temp2 reduce];
return ([temp1 numerator] == [temp2 numerator])
&& ([temp1 denominator] == [temp2 denominator]);
}
Upvotes: 0
Reputation: 52227
if (selfCopy == object)
this only checks, if the pointer is the same
try
-(BOOL) isEqualTo:(id)object
{
return self.numerator == object.numerator && self.denumerator == object.denumerator :
}
Okay, this is too simple, as [fracA setTo:1 over:4]
and [fracA setTo:2 over:8]
should probably be equal, but you should get the point.
The default implementation provided for many of these methods by NSObject is appropriate for objects that implement a single comparison method whose selector, signature, and description match the following:
- (NSComparisonResult)compare:(id)object;
This method should return NSOrderedAscending if the receiver is less than object, NSOrderedDescending if the receiver is greater than object, and NSOrderedSame if the receiver and object are equal. For example, NSString does not implement most of the methods declared in this informal protocol, but NSString objects still handle messages conforming to this protocol properly because NSString implements a compare: method that meets the necessary requirements. Cocoa also includes appropriate compare: method implementations for the NSDate, NSDecimalNumber, and NSValue classes.
So you should better have a -compare:
like
-(NSOrderResult) compare:(Fraction *)otherFraction
{
Fraction *selfReduced = [self fractionReduced]; // should return a unretaind reduced copy
Fraction *otherReduced= [otherFraction fractionReduced];
float selfAbs = (float)selfReduced.nominator / (float)selfReduced.denominator;
float otherAbs = (float)selfReduced.nominator / (float)selfReduced.denominator;
if (selfAbs > otherAbs) return NSOrderedAscending;
if (selfAbs > otherAbs) return NSOrderedDescending;
return NSOrderedSame;
}
Upvotes: 3
Reputation: 7720
if (selfCopy == object)
will always be false, because you are comparing pointers.
You have to implement a proper comparison of your instances.
cant I test object like this (selfCopy == object)? should I do selfCopy.numerator
No. You don't need a copy of self
. Also, you're not even creating a copy of self
, you're only allocating a new object. This is how it should look like.
-(BOOL)isEqualTo:(id)object
{
if (self.someValue == object.someValue &&
self.otherValue == object.otherValue)
return YES;
else
return NO;
}
Upvotes: 2