PDA

View Full Version : Key-Value Coding Question




Soulstorm
Feb 13, 2007, 03:17 PM
Sorry if this is a newbish question, but I have so far got used to make programs only by using very standard features that concern key-value coding. I have this simple piece of code:

#import <Foundation/Foundation.h>

@interface test:NSObject{
NSMutableString *simpleValue;
NSMutableArray *simpleArray;
}


@end


@implementation test:NSObject
- (id) init {
self = [super init];
if (self != nil) {
simpleValue = [NSMutableString stringWithString:@"hello world!"];
simpleArray = [NSMutableArray arrayWithObjects:@"hello 1", @"hello 2", nil];
}
return self;
}

- (void) dealloc {
[simpleValue release];
[simpleArray release];
[super dealloc];
}

@end

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

test *t = [[test alloc]init];
[t takeValue:@"hello again!" forKey:@"simpleValue"];
NSLog(@"%@",[t valueForKey:@"simpleValue"]);


[pool release];
return 0;
}

When ran, the debugger gives me a runtime error at the "[pool release]" line. Why is that? What is key-value coding in general, and how can I make my classes use it?



robbieduncan
Feb 13, 2007, 03:24 PM
What's the error?

Apple have a great guide to Key Value coding (http://developer.apple.com/documentation/Cocoa/Conceptual/KeyValueCoding/index.html?http://developer.apple.com/documentation/Cocoa/Conceptual/KeyValueCoding/Concepts/BasicPrinciples.html).

Basically it's a nice way to provide generic access to an objects properties in a predictable and controllable method. Bindings is built directly on top of this...

Soulstorm
Feb 13, 2007, 03:32 PM
What's the error?

Apple have a great guide to Key Value coding (http://developer.apple.com/documentation/Cocoa/Conceptual/KeyValueCoding/index.html?http://developer.apple.com/documentation/Cocoa/Conceptual/KeyValueCoding/Concepts/BasicPrinciples.html).

Basically it's a nice way to provide generic access to an objects properties in a predictable and controllable method. Bindings is built directly on top of this...

Actually, the debugger comes up, and it doesn't tell me what the error is. I guess you must compile and run it to see for yourself.

the following code gives me errors again...
#import <Foundation/Foundation.h>

@interface test: NSObject
{
NSString *simpleValue;
NSArray *simpleArray;
}

-(void)setSimpleValue:(NSString *)newValue;
-(void)setSimpleArray:(NSArray *)newArray;

-(NSArray *)getSimpleArray;
-(NSString *)getSimpleValue;

@end


@implementation test
- (id) init {
self = [super init];
if (self != nil) {
simpleValue = [NSMutableString stringWithString:@"hello world!"];
simpleArray = [NSMutableArray arrayWithObjects:@"hello 1", @"hello 2", nil];
}
return self;
}


-(void)setSimpleValue:(NSString *)newValue
{
[simpleValue release];
simpleValue = [newValue retain];
}

-(void)setSimpleArray:(NSArray *)newArray
{
[simpleArray release];
simpleArray = [newArray retain];
}


-(NSArray *)getSimpleArray
{
return simpleArray;
}

-(NSString *)getSimpleValue
{
return simpleValue;
}

- (void) dealloc {
[simpleValue release];
[simpleArray release];
[super dealloc];
}

@end

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


test *testClass = [[test alloc]init];

[testClass setValue:@"hello world!" forKey:@"simpleValue"];
NSLog([testClass getSimpleValue]);


[pool release];
return 0;
}


...but I don't know why

robbieduncan
Feb 13, 2007, 03:43 PM
Bad memory management...

When you create an instance of the test class you create two objects that are autoreleased (simpleValue and simpleArray). When you then call setSimpleValue this autoreleased object is released again. You should never release an object you have not retained...

So when your pool gets released it tries to release all the objects in it. But you've released it and it crashes.

If you retain the two objects it doesn't crash

A better solution to init is to do something like:


- (id) init {
self = [super init];
if (self != nil) {
[self setSimpleValue:@"hello world!"];
}
return self;
}


This will cause any bindings to get triggered: your way does not...

Soulstorm
Feb 13, 2007, 05:53 PM
That corrected the problem I was having. Thanks a lot robbieduncan!