Go Back   MacRumors Forums > Apple Systems and Services > Programming > Mac Programming

Reply
 
Thread Tools Search this Thread Display Modes
Old Jan 20, 2009, 07:45 AM   #1
mdeh
macrumors 6502
 
Join Date: Jan 2009
Exercise 9-4 Kochan 2.0. A question

Quote:
Based on the discussions about argument and return types in this chapter, modify both add: methods in the Fraction andComplex classes to take and return id objects. Then write a program that incorporates the following code sequence:
result = [dataValue1 add: dataValue2];
[result print];
where result, dataValue1, and dataValue2 are id objects. Make sure you set dataValue1 and dataValue2 appropriately in your program and free all objects before your program terminates.
Does this mean to modify EACH method so that EACH method can take a fraction or complex class object?
mdeh is offline   0 Reply With Quote
Old Jan 20, 2009, 09:37 AM   #2
skochan
macrumors regular
 
Join Date: Apr 2006
Location: California
 
Quote:
Originally Posted by mdeh View Post
Does this mean to modify EACH method so that EACH method can take a fraction or complex class object?
The Complex and Fraction classes both have add: methods. The exercise is to change the argument and return type of each add: method to take and return an id object.

Cheers,

Steve K.
skochan is offline   0 Reply With Quote
Old Jan 20, 2009, 02:14 PM   #3
mdeh
Thread Starter
macrumors 6502
 
Join Date: Jan 2009
Answer for 9-4???
Here is my attempt. Your input is appreciated.

Fraction.h
Code:
#import <Foundation/Foundation.h>
@interface Fraction : NSObject {
	int numerator;
	int denominator;
}
@property int numerator, denominator;
-(void) setTo: (int) n over: (int) d;
-(id) add: (id) f;
-(void) reduce;

Code:
#import "Fraction.h"


@implementation Fraction;
@synthesize denominator, numerator;
-(void) print 
{
	
	NSLog(@"%i/%i ", numerator, denominator);
}

-(void) setTo: (int) n over: (int) d
{
	numerator = n;
	denominator = d;
}


-(id) add: (id) f
{
	int resultNum, resultDenom;
	Fraction* result = [[Fraction alloc] init];
	
	resultNum = numerator *[ f denominator] + denominator * [f numerator];
	resultDenom = denominator *[ f denominator];
	
	[result setTo: resultNum over: resultDenom];
	[result reduce];
	return result;
}

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

-(void) reduce
{
	int u, v, temp;
	BOOL isNegativeNumerator = NO;
	BOOL isNegativeDenominator = NO;
	
	if ( numerator < 0)
	{
		isNegativeNumerator = YES;
		numerator = -numerator;
	}
	
	
	if ( denominator < 0)
	{
		isNegativeDenominator = YES;
		denominator = -denominator;
	}
	
	u = numerator;
	v = denominator;
	
	
	while (v != 0) {
		temp = u % v;
		u = v;
		v = temp;
	}
	
	
	
	numerator /= u;
	denominator /= u;
	
	
	
	if ( isNegativeNumerator == YES || isNegativeDenominator == YES)
		numerator = -numerator;
}

@end

Complex.h

Code:
#import <Foundation/Foundation.h>

@interface Complex : NSObject
{
	float real;
	float imaginary;
}

@property float real, imaginary;
-(id) add: (id) complexNumber; 
-(void) setReal: (float) r andImaginary: (float) i;
-(void) print;
@end
Complex.m

Code:
#import "Complex.h"
@implementation Complex

@synthesize real, imaginary;

-(void) setReal: (float) r andImaginary: (float) i
{
	real = r;
	imaginary = i;
}

-(id) add: (id) complexNumber
{
	Complex *myCx =  [[ Complex alloc ] init];
	myCx.real = (real + [complexNumber real]);
	myCx.imaginary = (imaginary + [complexNumber imaginary]);
	return myCx;
	
}
-(void) print
{
	NSLog(@"%g + %gi", real, imaginary);
}
@end
main.m

Code:
#import "Fraction.h"
#import "Complex.h"

int main (int argc, const char * argv[]) {
    NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
	id dataVal1, dataVal2, result;
	Complex *c1 = [[ Complex alloc] init];
	Complex *c2 = [[ Complex alloc] init];
	Fraction *f1 = [ [ Fraction alloc] init];
	Fraction *f2 = [ [ Fraction alloc] init];
	
	[c1 setReal: 67.0	andImaginary: 76.0];
	[c2 setReal: 27.0	andImaginary: 72.0];
	dataVal1 = c1;
	dataVal2 = c2;
	
	result = [dataVal1 add: dataVal2];
	[result print];
	
	[result release];
	
	[f1 setTo: 4 over: 5];
	[f2 setTo: 7 over: 8];
	
	dataVal1 = f1;
	dataVal2 = f2;
	
	result = [ dataVal1 add: dataVal2];
	[result print];
	[result release];
	
	
	
	[f1 release];
	[f2 release];
	[c1 release];
	[c2 release];
    [pool drain];
    return 0;
}
mdeh is offline   0 Reply With Quote
Old Jan 20, 2009, 05:45 PM   #4
TotalLuck
macrumors newbie
 
Join Date: Jan 2009
Location: Moreno Vallley
Send a message via Yahoo to TotalLuck
thanks Mdeh

Thanks a ton. again i was about to ask for help and there you are posting.

After pulling my hair out i see what was perplexing me.

I was trying to use f.numerator instead of [ f numerator].

So if i understand it , the dot notation is used when you/program knows what to expect from the object that was passed in. The [ f numerator] is basically saying go get this item. ( i had tried [f getNumerator] )

i don't have a problem getting the program to compile using the following
Code:
from fraction .m
-(id) add: (id) f
{   //add fractions together
	
	// result stores the reult of the addition
	
	
		Fraction *result = [[Fraction alloc] init];
		double resultNum, resultDenom , fnum ;
	
	if ( f < 0)
	{
		
		fnum = -1 * [f numerator];
		resultNum = numerator * [f denominator ] - denominator * fnum ;
		resultDenom = denominator * [f denominator];
		[result setTo:resultNum over: resultDenom];
	}
	
	else 
	{
		
		resultNum = numerator * [f denominator ]  + (denominator * [ f numerator ]);
		resultDenom = denominator * [  f denominator ];
		[result setTo:resultNum over: resultDenom];
	}
	if (resultNum > resultDenom)
	{	
		[result reduce];
	
	}
	
	return result;
	
}

int main(int argc, char *argv[])
{
	NSAutoreleasePool * pool = [[NSAutoreleasePool alloc]init];

	id  result, dataValue2, dataValue1;
	Fraction *f1 = [[Fraction alloc]init];
	Fraction *f2 = [[Fraction alloc]init];
	ComplexNumbers *c1 = [[ ComplexNumbers alloc] init];
	ComplexNumbers *c2 = [[ ComplexNumbers alloc] init];

	[f1 setTo:2 over:5];
	[f2 setTo:5 over:8];
	
	result = [ f1 add: f2];
	[result print];
but when i add
Code:
	dataValue1 = f1;
	dataValue2 = f2;
	
	result = [ dataValue1 add: dataValue2 ];
	[result print];
	[result release];
i get error
" - void value not ignored as it ought to be. "
what am i missing there?
__________________
Finding my inner Nerd
NEVER EVER make a drunken bet or you could wind up with a picture like mine.
TotalLuck is offline   0 Reply With Quote
Old Jan 20, 2009, 06:25 PM   #5
mdeh
Thread Starter
macrumors 6502
 
Join Date: Jan 2009
Quote:
Originally Posted by TotalLuck View Post
I was trying to use f.numerator instead of [ f numerator].
There clearly is a difference. Perhaps one of the more erudite contributors could clear this up?


Code:
i get  error 
" - void value not ignored as it ought to be. "
what am i missing there?[/QUOTE]

I am not sure if this would make any difference, but are you releasing "result" before you use it again?
mdeh is offline   0 Reply With Quote
Old Jan 20, 2009, 07:13 PM   #6
skochan
macrumors regular
 
Join Date: Apr 2006
Location: California
 
Quote:
Originally Posted by TotalLuck View Post
Thanks a ton. again i was about to ask for help and there you are posting.

After pulling my hair out i see what was perplexing me.

I was trying to use f.numerator instead of [ f numerator].

So if i understand it , the dot notation is used when you/program knows what to expect from the object that was passed in.
That's right! The dot notation cannot be used directly on id variables (you'd have to typecast it first to the appropriate object type). I should have pointed that out in the text--and I'll get it into the next printing.

Quote:
Originally Posted by TotalLuck View Post
but when i add
Code:
	dataValue1 = f1;
	dataValue2 = f2;
	
	result = [ dataValue1 add: dataValue2 ];
	[result print];
	[result release];
i get error
" - void value not ignored as it ought to be. "
what am i missing there?
Without seeing all the code, I'm guessing you have the add: method declared to return void somewhere (perhaps in the ComplexNumbers.h/.m files?). Let me know, or email the complete code to me.

Cheers,


Steve Kochan
skochan is offline   0 Reply With Quote
Old Jan 20, 2009, 07:40 PM   #7
TotalLuck
macrumors newbie
 
Join Date: Jan 2009
Location: Moreno Vallley
Send a message via Yahoo to TotalLuck
Thanks again steve.

Here are the files
Code:
#import <Foundation/Foundation.h>
#import <objc/Object.h>

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

@property int numerator, denominator;

-(void) print;
-(double) convertToNum;
-(void) setTo: (int) n over: (int) d;
-(id) add:(id) f;
-(Fraction *) subtract: (Fraction *) f;
-(Fraction *) multiply: (Fraction *) f;
-(Fraction *) divide: (Fraction *)f;
-(void) reduce;


@end
Code:
#import "Fraction.h"


@implementation Fraction
@synthesize numerator, denominator;

-(void) print
{
	int whole, num2;
	BOOL needToReduce;
	
	if  ( numerator >= denominator)
		needToReduce = YES;
	
	
	if (needToReduce == YES)
	{
		whole = numerator / denominator;
		num2 = numerator % denominator;
		if (numerator % denominator == 0)
			NSLog(@" %i ", whole);
		else	
			NSLog(@" %i %i/%i ", whole, num2, denominator);
	}
	else
		NSLog(@" %i/%i ",numerator, denominator);
}

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

-(void) setTo: (int) n over: (int) d
{
	numerator = n;
	denominator = d;
}


-(id) add: (id) f
{   //add fractions together
	
	// result stores the reult of the addition
	
	
		Fraction *result = [[Fraction alloc] init];
		double resultNum, resultDenom , fnum ;
	
	if ( f < 0)
	{
		
		fnum = -1 * [f numerator];
		resultNum = numerator * [f denominator ] - denominator * fnum ;
		resultDenom = denominator * [f denominator];
		[result setTo:resultNum over: resultDenom];
	}
	
	else 
	{
		
		resultNum = numerator * [f denominator ]  + (denominator * [ f numerator ]);
		resultDenom = denominator * [  f denominator ];
		[result setTo:resultNum over: resultDenom];
	}
	if (resultNum > resultDenom)
	{	
		[result reduce];
	
	}
	
	return result;
	
}
	
-(Fraction *) subtract: (Fraction *) f
{
	//subtract fractions
	Fraction *result = [[Fraction alloc] init];
	int resultNum1, resultNum2, resultDenom, resultNum;
	
	
	if ( f < 0)
	{
		f.numerator = -1 * f.numerator;
		
		resultNum1 =(numerator * f.denominator) ;
		resultNum2 = (denominator * f.numerator);
		resultDenom = (denominator * f.denominator);
		
		resultNum = resultNum1 + resultNum2;
		
		[result setTo:resultNum		over: resultDenom];
	}
	
	else {
		
		resultNum1 =(numerator * f.denominator) ;
		resultNum2 = (denominator * f.numerator);
		resultDenom = (denominator * f.denominator);
		
		resultNum = resultNum1 - resultNum2;
		
		[result setTo:resultNum		over: resultDenom];
	}
	
	if (resultNum > resultDenom)
	{	
		[result reduce];
	}
	
	
	return result;
}
-(Fraction *) multiply: (Fraction *) f
{
	Fraction *result = [[Fraction alloc]init];
	int resultNum, resultDenom;
	
	
	if ( f < 0)
	{
		f.numerator = -1 * f.numerator;
		
		resultNum = numerator * f.numerator;
		resultDenom = denominator * f.denominator;
		
		[result setTo:resultNum over: resultDenom];
	}
	else 
	{
		
		resultNum = numerator * f.numerator;
		resultDenom = denominator * f.denominator;
		
		[result setTo:resultNum over: resultDenom];
	}
	
	if (resultNum > resultDenom)
	{	
		result.reduce;
	}
	
	return result;
}


-(Fraction *) divide: (Fraction *)f
{
	Fraction *result = [[Fraction alloc]init];
	int resultNum, resultDenom;
	
	resultNum = numerator * f.denominator;
	resultDenom = denominator * f.numerator;
	
	[result setTo:resultNum over: resultDenom];
	
	if (resultNum > resultDenom)
	{	
		result.reduce;
	}
	
	
	return result;
}



-(void) reduce
{
	int u = numerator;

	int v = denominator;
	int temp;
	
	
	
	while ( v != 0)
	{
		temp = u % v;
		u = v;
		v = temp;
	}
	
	numerator /= u;
	denominator /= u;
	
}


@end
Code:
#import <Cocoa/Cocoa.h>
#import <Foundation/Foundation.h>


@interface ComplexNumbers : NSObject
{
	double	real;
	double	imaginary;
}

@property double real, imaginary;

// methods 
-(void) setReal : (double) a andImaginary: (double) b;
-(void) print; // to print as  a + b(i)
-(id) add: (id)  c;




@end
Code:
#import "Complex.h"


@implementation ComplexNumbers

@synthesize real, imaginary;
// define methods
-(id) add: (id) c
{
	id result = [[ComplexNumbers alloc] init];
	double r1, imag1;
	
	r1		= real + [c real];
	imag1	= imaginary + [c imaginary];
	[result setReal:r1 andImaginary:imag1];
	
	return result;
	
}
-(void) setReal: (double) a  andImaginary: (double) b
{
	real = a , imaginary = b;
}

-(void) print  //  print the equation
{
	NSLog(@"(%g + %gi)", real, imaginary);
}

@end
Code:
#import <Foundation/Foundation.h>
#import "Fraction.h"
#import "Complex.h"


int main(int argc, char *argv[])
{
	NSAutoreleasePool * pool = [[NSAutoreleasePool alloc]init];

	id  result, dataValue2, dataValue1;
	Fraction *f1 = [[Fraction alloc]init];
	Fraction *f2 = [[Fraction alloc]init];
	ComplexNumbers *c1 = [[ ComplexNumbers alloc] init];
	ComplexNumbers *c2 = [[ ComplexNumbers alloc] init];

	[f1 setTo:2 over:5];
	[f2 setTo:5 over:8];
	
	result = [ f1 add: f2];
	[result print];
	
	dataValue1 = f1;
	dataValue2 = f2;
	result = [ dataValue1 add: dataValue2 ];

	[result print];

	
	[c1 setReal: 10 andImaginary: 2.5 ];
	[c2 setReal: 14 andImaginary: 3];
	
	result = [ c1 add: c2 ];
	[result print];
	
	dataValue1 = c1;
	dataValue2 = c2;
	
	result = [ dataValue1 add: dataValue2 ];
	
	[result print];
	[result release];
	
	[c1 release];
	[c2 release];
	[f2 release];
	[f1 release];
	[pool drain];
	return 0;
	
	
}
i am using Xcode leopard 10.5

here is the debug
Code:
/users/lori/Desktop/Objectve c lessons/Rectangle/main.m: In function 'main':
/Users/lori/Desktop/Objectve c lessons/Rectangle/main.m:32: warning: multiple methods named '-add:' found
/Developer/SDKs/MacOSX10.5.sdk/System/Library/Frameworks/AppKit.framework/Headers/NSObjectController.h:59: warning: using '-(void)add:(id)sender'
/Users/lori/Desktop/Objectve c lessons/Rectangle/Fraction.h:22: warning: also found '-(id)add:(id)f'
/Users/lori/Desktop/Objectve c lessons/Rectangle/main.m:32: error: void value not ignored as it ought to be
/Users/lori/Desktop/Objectve c lessons/Rectangle/main.m:46: warning: multiple methods named '-add:' found
/Developer/SDKs/MacOSX10.5.sdk/System/Library/Frameworks/AppKit.framework/Headers/NSObjectController.h:59: warning: using '-(void)add:(id)sender'
/Users/lori/Desktop/Objectve c lessons/Rectangle/Fraction.h:22: warning: also found '-(id)add:(id)f'
/Users/lori/Desktop/Objectve c lessons/Rectangle/main.m:46: error: void value not ignored as it ought to be
does it look like an error in the framework file?
__________________
Finding my inner Nerd
NEVER EVER make a drunken bet or you could wind up with a picture like mine.
TotalLuck is offline   0 Reply With Quote
Old Jan 20, 2009, 08:14 PM   #8
skochan
macrumors regular
 
Join Date: Apr 2006
Location: California
 
Quote:
Originally Posted by TotalLuck View Post
/[B]Developer/SDKs/MacOSX10.5.sdk/System/Library/Frameworks/AppKit.framework/Headers/NSObjectController.h:59: warning: using '-(void)add: (id)sender'
[/CODE]
does it look like an error in the framework file?
Looks like the NSObjectController class has an add: method that returns void; thus the conflict at compile time. Use different method names (like addX). This goes back to the point made in the text about sending a message to an id type: all methods of the same name must agree in arguments and return type. This is actually a good learning exercise

By the way, you shouldn't be importing <objC/Object.h> . I don't have my book handy, but if that's from the text, it's a holdover from the first edition.

-----------
From Apple's documentation on the NSObjectController class:

add:
Creates a new object and sets it as the receiver’s content object.

- (void)add: (id)sender

Parameters
sender
Typically the object that invoked this method.
....

-------------

Cheers,

Steve Kochan
skochan is offline   0 Reply With Quote
Old Jan 21, 2009, 01:20 PM   #9
TotalLuck
macrumors newbie
 
Join Date: Jan 2009
Location: Moreno Vallley
Send a message via Yahoo to TotalLuck
Thank you Steve

Quote:
Originally Posted by skochan View Post
By the way, you shouldn't be importing <objC/Object.h> . I don't have my book handy, but if that's from the text, it's a holdover from the first edition.
Yeah i forgot to delete that.. I worked through the first 5 chapters in Book 1 then got Book 2 and forgot to change some of the file #imports. so dont chase down the editor just yet.

and thanks for the help. changing to the -(id)addX fixed the problem.
__________________
Finding my inner Nerd
NEVER EVER make a drunken bet or you could wind up with a picture like mine.
TotalLuck is offline   0 Reply With Quote
Old Jan 21, 2009, 03:12 PM   #10
mdeh
Thread Starter
macrumors 6502
 
Join Date: Jan 2009
Quote:
Originally Posted by skochan View Post
That's right! The dot notation cannot be used directly on id variables (you'd have to typecast it first to the appropriate object type). I should have pointed that out in the text--and I'll get it into the next printing.
Steve, I thought the "typecast" operator was () as in:

return (float) 7 /* where 7 is an int */

Here we use [ ..... ]. Could you elaborate a little.

Thank you.
mdeh is offline   0 Reply With Quote
Old Jan 21, 2009, 04:20 PM   #11
skochan
macrumors regular
 
Join Date: Apr 2006
Location: California
 
Quote:
Originally Posted by mdeh View Post
Steve, I thought the "typecast" operator was () as in:

return (float) 7 /* where 7 is an int */

Here we use [ ..... ]. Could you elaborate a little.

Thank you.
Ahh, I was hoping you wouldn't ask me that. If you knew the id object f was a Fraction, you could write the following:

Code:
((Fraction *) f).numerator
I'm only showing you this because you asked. But it's ugly!

Cheers,

Steve Kochan
skochan is offline   0 Reply With Quote

Reply
MacRumors Forums > Apple Systems and Services > Programming > Mac Programming

Thread Tools Search this Thread
Search this Thread:

Advanced Search
Display Modes

Similar Threads
thread Thread Starter Forum Replies Last Post
Learning Obj C - Kochan or Big Nerd Ranch? afousek iPhone/iPad Programming 4 Apr 26, 2014 01:45 PM

Forum Jump

All times are GMT -5. The time now is 10:22 PM.

Mac Rumors | Mac | iPhone | iPhone Game Reviews | iPhone Apps

Mobile Version | Fixed | Fluid | Fluid HD
Copyright 2002-2013, MacRumors.com, LLC