objective-ciosxmlxml-parsingtouchxml

NSRangeException for empty array except there is an array?


I'm having this problem where I keep getting this error in my console:

* Terminating app due to uncaught exception 'NSRangeException', reason: '* -[__NSArrayI objectAtIndex:]: index 0 beyond bounds for empty array'

Here is my code for retrieving the data from the XML document:

CXMLDocument *worldweather = [[CXMLDocument alloc]initWithContentsOfURL:[NSURL URLWithString:[NSString stringWithFormat:@"http://free.worldweatheronline.com/feed/weather.ashx?q=%@&format=xml&num_of_days=4&key=0ded69e02b171832121504",query]] options:0 error:nil];

weathercondition = [[[worldweather nodesForXPath:@"/data/current_condition/weatherIconUrl" error:nil] objectAtIndex:0] stringValue];

The location that Xcode is using is Williams, CA and the query sent is

Williams+CA

When I plug this into my URL, it works and I get my XML file, but why am I getting this message in my console???

This is driving me crazy. All help would be GREATLY appreciated! Thanks in advance!


Solution

  • Seems that you think that [worldweather nodesForXPath:@"/data/current_condition/weatherIconUrl" error:nil] is NSArray with at least one object inside the array. This is clearly not the case, and you get an error saying that there is no object at index 0, which means that array is empty.

    If you are not sure there is at least one object inside an NSArray do not just call objectAtIndex:0.

    You could first check how many elements are there in array and then do the work like:

    NSArray *weatherArray = [worldweather nodesForXPath:@"/data/current_condition/weatherIconUrl" error:nil];
    
    if ([weatherArray count] > 0){
      weathercondition = [[weatherArray objectAtIndex:0] stringValue];
    }
    

    If you are not sure what you are getting back from the server, see what is in the array:

    NSLog(@"%@", weatherArray);
    

    or check how many elements there are:

    NSLog(@"elements in Array: %i", [weatherArray count]);
    

    One additional useful thing you can use is for example [weatherArray lastObject], this will always return the last element of the array and will return nil even if the array is empty (it will not crash like objectAtIndex:0)