Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

IOS App crash: [__NSArrayI objectAtIndex:]: index 0 beyond bounds for empty array

I have a method I pass an 'id' into here:

NSString *id = @"4bf58dd8d48988d181941735";
[self getNames:id];

This works fine, but when I use the 'id' from an object passed within the segue:

NSString *id = _selectedStore._id;
[self getNames:id];

I get the error:

'NSRangeException', reason: '*** -[__NSArrayI objectAtIndex:]: index 0 beyond bounds for empty array'

What's going on?

Here's where it's getting the error. My attempt (keep in mind i'm new at this) is to take an array of Foursquare id's, get the names and then get the photoUrl for the id's. If I remove all code that creates the photoUrl (i've noted in the code) it runs without crashing.

- (void)getNames {
    NSMutableArray *final = [[NSMutableArray alloc] init];
    for (SearchVenue *object in self.venues) {
    [Foursquare2 venueGetDetail:object._id  callback:^(BOOL success, id result){
            if (success) {
                NSDictionary *dic = result;
                NSArray *venue = [dic valueForKeyPath:@"response.venue"];
                self.venueDetail = venue;                
                NSMutableDictionary *newVen = [NSMutableDictionary dictionary];
                [newVen setValue:[self.venueDetail valueForKey:@"name"] forKey:@"name"];
                [final addObject:newVen];
                    [Foursquare2 venueGetPhotos:object._id limit:nil offset:nil callback:^(BOOL success, id result){
                        if (success) {

                            NSDictionary *dic = result;
                            NSArray *photos = [dic valueForKeyPath:@"response.photos"];
                            self.venuePhotos = photos;

                             //works when removed from here...
                            NSString *prefix = [[self.venuePhotos valueForKeyPath:@"items.prefix"] objectAtIndex:0];
                            NSString *size = @"100x100";
                            NSString *suffix = [[self.venuePhotos valueForKeyPath:@"items.suffix"] objectAtIndex:0];
                            NSArray *myStrings = [NSArray arrayWithObjects:prefix,size,suffix, nil];
                            NSString *photoUrl = [myStrings componentsJoinedByString:@"" ];
                            //...to here

                            NSMutableDictionary *newVen1 = [NSMutableDictionary dictionary];
                                [newVen1 setValue:photoUrl forKey:@"photoUrl"];
                            for(int i = 0; i < [final count]; i++) {
                               [[final objectAtIndex:i] addEntriesFromDictionary:newVen1];
                            }
                            _arrayOfPlaces = final;
                            NSLog(@"_arrayOfPlaces is %@",_arrayOfPlaces);
                            [self.resultsVC reloadData];
                        } else {
                            NSLog(@"%@",result);
                        }
                    }];
            } else {
                NSLog(@"%@",result);
              }
        }];
    }
}
like image 645
Ryasoh Avatar asked Dec 02 '14 06:12

Ryasoh


1 Answers

Your problem is probably here:

NSString *prefix = 
 [[self.venuePhotos valueForKeyPath:@"items.prefix"] objectAtIndex:0];

You should do this:

if ([[self.venuePhotos valueForKeyPath:@"items.prefix"] count] > 0) {
NSString *prefix = 
 [[self.venuePhotos valueForKeyPath:@"items.prefix"] objectAtIndex:0]
...
} else {
// Do something for not having the prefix
}

if you want to be ultra-safe, which is always good, do this

if ([[self.venuePhotos valueForKeyPath:@"items.prefix"] 
                         isKindOfClass:[NSArray class]] 
 && [[self.venuePhotos valueForKeyPath:@"items.prefix"] count] > 0)

This will also ensure the item is an array. If 1[self.venuePhotos valueForKeyPath:@"items.prefix"]1 isn't and it doesn't respond to count, it will crash.

Generalized rule of thumb, which is seldom consistently followed is always check bounds prior to accessing an array using an index. This is regardless of whether you get it by subscript or objectAtIndex.

like image 182
Mobile Ben Avatar answered Nov 05 '22 08:11

Mobile Ben