fuzzygoat
fuzzygoat

Reputation: 26223

Class Composition Error?

I wonder if someone can explain where I am going wrong here, I am creating 2 objects (car & engine) where the car object contains a pointer to the engine object. I know I am missing the obvious or just making some silly mistake, but I can't quite put my finger on it.

NB: the code all works, except for the line that is comment ERROR.

// INTERFACE ------------------------------------------------------- **
@interface EngineClass : NSObject {
}
@end


@interface CarClass : NSObject {
    EngineClass *engine;
}
- (void)setEngine:(EngineClass *)value;
@end


// IMPLEMENT ------------------------------------------------------- **
@implementation CarClass

- (void)setEngine:(EngineClass *)newEngine {
    if (engine != newEngine) {
        [engine release];
        engine = [newEngine copy];
    }
}
@end

@implementation EngineClass
@end


// MAIN ------------------------------------------------------------ **

#import <Foundation/Foundation.h>

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

    CarClass *newCar_001;
    EngineClass *newEngine_001;

    newCar_001 = [[CarClass alloc] init];
    newEngine_001 = [[EngineClass alloc] init];

    [newCar_001 setEngine: newEngine_001]; // ERROR

    // Clean up
    [newCar_001 release];
    [newEngine_001 release];
    [pool drain];
    return 0;
}
// END ------------------------------------------------------------- **

The ERROR is ....

run 2009-09-22 13:41:05.483 cocoa_engine_TEST[8606:a0f] 2009-09-22 13:41:05.485 cocoa_engine_TEST[8606:a0f] 2009-09-22 13:41:05.485 cocoa_engine_TEST[8606:a0f] -[EngineClass copyWithZone:]: unrecognized selector sent to instance 0x10010c8d0 2009-09-22 13:41:05.486 cocoa_engine_TEST[8606:a0f] *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[EngineClass copyWithZone:]: unrecognized selector sent to instance 0x10010c8d0'

cheers -gary-

Upvotes: 0

Views: 228

Answers (1)

Terry Wilcox
Terry Wilcox

Reputation: 9040

From the docs for the copy method:

This is a convenience method for classes that adopt the NSCopying protocol. An exception is raised if there is no implementation for copyWithZone:.

Have you implemented copyWithZone?

And why copy engine when you could just retain?

- (id)copyWithZone:(NSZone *)zone {
    EngineClass *engineCopy = [[EngineClass allocWithZone: zone] init];
    // copy variables here, deep or shallow
    return engineCopy;
}

It returns a retained object, as copy methods should.

Upvotes: 3

Related Questions