user973985
user973985

Reputation: 291

NSMutableArray's count method throws an exception when called in expression

 if ([diamonds count] == 0) {
    [self toggleWinLevel];
}

When diamonds is an NSMutableArray and toggleWinLevel is an instance method, if I run this app it crashes on this line with an EXC_BAD_ACCESS:

 if ([diamonds count] == 0) {

It is is definitely to do with my array since this keeps on happening even when i assign an int or NSUInteger or NSNumber to my array's count. My NSMutableArray is allocated and initialized. What is the problem?

UPDATE 1:

Ive allocated and initialized it in this method which DOES get called and i have NSLog which does log in the console for proof:

    -(void)setUpObjects {

NSLog(@"Setting Up Objects"); // This is printed in my console

[levelNumberLabel setHidden:YES];
diamonds = [[NSMutableArray alloc] init];
rocks = [[NSMutableArray alloc] init];

if (levelNumber < 3) {

    diamonds = [NSMutableArray arrayWithObjects:@"1", nil];

} else if (levelNumber > 2 <= 4) {

    diamonds = [NSMutableArray arrayWithObjects:@"1", @"2", @"3", nil];

} else if (levelNumber > 4 <= 6) {

    diamonds = [NSMutableArray arrayWithObjects:@"1", @"2", @"3", @"4", nil];

} else if (levelNumber > 6 <= 10) {

    diamonds = [NSMutableArray arrayWithObjects:@"1", @"2", @"3", @"4", @"5", nil];

} else if (levelNumber > 10) {

    diamonds = [NSMutableArray arrayWithObjects:@"1", @"2", @"3", @"4", @"5", @"6", nil];
}

if ([diamonds count] > 1 <= 2) {

    rocks = [NSMutableArray arrayWithObjects:@"1", @"2", nil];                 

} else if ([diamonds count] > 2 <= 5) {

    rocks = [NSMutableArray arrayWithObjects:@"1", @"2", @"3", nil];

} else if ([diamonds count] > 5) {

    rocks = [NSMutableArray arrayWithObjects:@"1", @"2", @"3", @"4", nil];
}

[self drawObjects];
}

BTW diamonds (the array) is an instance variable

Upvotes: 0

Views: 692

Answers (3)

jrturton
jrturton

Reputation: 119292

Either do what ThomasW suggests and retain the new array (but this will leak your original instance) or simply add items into the array instead of creating a new one:

diamonds = [NSMutableArray arrayWithObjects:@"1", nil];

Should read

[diamonds addObjectsFromArray:[NSArray arrayWithObjects:@"1", nil]];

This adds objects into an existing array instead of creating a new one.

You have already created the diamonds array with your alloc/init, you are recreating it as an autoreleased variable within your if statements.

The same applies to your rocks array.

Upvotes: 2

ThomasW
ThomasW

Reputation: 17317

You are first calling:

diamonds = [[NSMutableArray alloc] init];

but later calling, for example:

diamonds = [NSMutableArray arrayWithObjects:@"1", nil];

The second call will assign to diamonds an autoreleased object, you need to retain that object.

There is an inconsistency in your code in that with your first call you have an retained object as opposed to an autoreleased object in the second call.

Upvotes: 2

Denis
Denis

Reputation: 6413

Most likely you're overreleasing the diamonds array, by other words, array object is already deallocated and you're trying to call a method for it. Use NSZombieEnabled=YES argument or Instruments with Zombies.

Upvotes: 2

Related Questions