In an iPhone app I'm developing, I grab a set of data from a web service, store it in a mutable array for showing in a table, and also store it in core data as backup when there is no network.
My array is initialized in application:didFinishLaunchingWithOptions: as follows
tableArray = [[NSMutableArray alloc] initWithCapacity:100];
the array is then filled after viewDidLoad gets called, meaning the UITableView exists (verified by checking debugger), and just before reloadData is called, I have NSLog print out the contents of the array, and sure enough everything is there.
My problem is that after reloadData is called, tableArray becomes null, as shown by an NSLog in tableView:numberOfRowsInSection:.
I'm at a complete loss as to why this is happening, though I've only been programming in Cocoa for a few months and could easily be missing something obvious.
EDIT: Updated with basic code.
@interface MyAppDelegate : NSObject {
...
NSMutableArray *tableArray;
}
@property (nonatomic, retain) NSMutableArray *tableArray;
...
@end
@implementation MyAppDelegate
@synthesize tableArray
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
tableArray = [[NSMutableArray alloc] initWithCapacity:100];
masterViewController = [[MasterViewController alloc] initWithNibName:@"MasterViewController" bundle:[NSBundle mainBundle]];
[masterViewController.tableView setDelegate:self];
[masterViewController.tableView setDataSource:self];
...
}
A method called runWithNetwork is then called in masterViewController's viewDidLoad:
- (void)runWithNetwork {
...
NSArray *backpackArray = [[mainDict objectForKey:@"items"] objectForKey:@"item"];
NSLog(@"%i", [backpackArray count]);
for (int a=0; a<[backpackArray count]; a++) {
NSDictionary *itemDict = [backpackArray objectAtIndex:a];
NSString *ID = [[itemDict valueForKey:@"defindex"] stringValue];
NSString *level = [[itemDict valueForKey:@"level"] stringValue];
NSString *quality = [[itemDict valueForKey:@"quality"] stringValue];
NSString *inventory = [[itemDict valueForKey:@"inventory"] stringValue];
NSNumber *uid = [NSNumber numberWithInt:a];
//Insert new
myItem = [NSEntityDescription insertNewObjectForEntityForName:@"Backpack" inManagedObjectContext:managedObjectContext_];
[myItem setValue:level forKey:@"level"];
[myItem setValue:inventory forKey:@"inventory"];
[myItem setValue:quality forKey:@"quality"];
[myItem setValue:uid forKey:@"uid"];
//Link to item db
NSFetchRequest *fetch = [[NSFetchRequest alloc] init];
NSPredicate *predicate = [NSPredicate predicateWithFormat:@"id == %@", ID];
[fetch setEntity:[NSEntityDescription entityForName:@"GlobalItems" inManagedObjectContext:managedObjectContext_]];
[fetch setPredicate:predicate];
item = [[managedObjectContext_ executeFetchRequest:fetch error:nil] objectAtIndex:0];
[myItem setValue:item forKey:@"item"];
[tableArray addObject:[item valueForKey:@"name"]]; //a series of nsstrings
}
NSLog(@"%@, %i", tableArray, [tableArray retainCount]); // all strings are printed correctly here, retaincount is 1
[masterViewController.tableView reloadData];
}
Then I go to my table methods:
- (NSInteger)tableView:(UITableView *)tView numberOfRowsInSection:(NSInteger)section {
NSLog(@"%@, %i", tableArray, [tableArray retainCount]); //(null) printed, 0 for retaincount
return [tableArray count]; //returns 0
}
The tableView is in the MasterViewController's xib, and is linked up correctly there. It is only ever described in MasterViewController and is set up as an IBOutlet. tableArray is only described in MyAppDelegate.h and is not re-created anywhere else.