Мне интересно, как правильно сделать копию объекта, определенного в делегате приложения, или одноэлементного объекта. Короче говоря, я делаю приложение, которое требует пользователя для входа в систему. Это представление входа в систему является просто модальным контроллером представления поверх «реального» приложения, которое состоит из tabbarcontroller и некоторых контроллеров табличного представления. После успешного входа в систему происходит отправка запроса данных на удаленный сервер, и контроллер модального представления отклоняется, показывая контроллер панели вкладок и представления таблицы, содержащие данные XML. Для разбора входящих данных я создал одноэлементный объект с именем DataParser, который имеет интерфейс
...
@interface DataParser : NSObject {
// Data objects that hold the data obtained from XML files
NSMutableDictionary *personnel;
NSMutableDictionary *schedule;
NSMutableDictionary *today;
}
@property (nonatomic, retain) NSMutableDictionary *personnel;
@property (nonatomic, retain) NSMutableDictionary *schedule;
@property (nonatomic, retain) NSMutableDictionary *today;
...
Теперь в этих словарях я храню (изменяемые) словари и массивы, содержащие объекты NSString с проанализированными данными XML. Поскольку я не хочу изменять эти исходные объекты, содержащие проанализированные данные (то есть я хочу изменить их только на этапе входа в систему, но не в любом из контроллеров таблиц), я создаю новый объект словаря, который содержит копия содержимого одного из словарей выше в каждом контроллере таблицы. Так, например, в loadView контроллера представления с именем ScheduleViewController у меня есть
...
@interface ScheduleViewController : UITableViewController {
NSDictionary *copyOfSchedule;
}
@property (nonatomic, retain) NSDictionary *copyOfSchedule;
...
@end
@implementation ScheduleViewController
@synthesize copyOfSchedule;
- (void)loadView {
[super loadView];
DataParser *sharedSingleton = [DataParser sharedInstance];
self.copyOfSchedule = [NSDictionary dictionaryWithDictionary:sharedSingleton.schedule];
}
...
Теперь это, кажется, работает нормально. Однако единственная трудность возникает, когда пользователь выходит из системы, что влечет за собой возвращение контроллера модального представления входа в стек. Когда пользователь снова нажимает кнопку входа в систему, то на сервер отправляется новый запрос данных XML, и словари в объекте singleton обновляются (новыми) данными (я проверяю, содержат ли они какие-либо данные, если так, то я вызываю removeAllObjects перед тем, как снова заполняя их вновь проанализированными данными). На этом этапе словари во всех контроллерах представления также должны быть обновлены, однако я не совсем уверен, как поступить правильно. Я заметил, что loadView не всегда вызывается снова в этом случае, и поэтому для этого я добавил тот же код, что и выше, в loadView для каждого метода viewWillAppear. После перехода назад и вперед между различными представлениями или перехода назад и вперед между дочерними представлениями представления таблицы, однако, я получаю ошибку EXC_BAD_ACCESS. Я подозреваю, что это связано с неправильным сохранением копий оригинальных словарей, но, похоже, я не могу найти решение этой проблемы. Вместо использования dictionaryWithDictionary, который, как я подозреваю, является неправильным, я также попробовал другой подход, где вместо использования объектов типа NSDictionary в ScheduleViewController я использую NSMutableDictionary. Итак:
...
@interface ScheduleViewController : UITableViewController {
NSMutableDictionary *copyOfSchedule;
}
@property (nonatomic, retain) NSMutableDictionary *copyOfSchedule;
...
@end
@implementation ScheduleViewController
@synthesize copyOfSchedule;
- (void)loadView {
[super loadView];
DataParser *sharedSingleton = [DataParser sharedInstance];
self.copyOfSchedule = [[NSMutableDictionary alloc] initWithDictionary:sharedSingleton.schedule];
}
- (void)viewWillAppear {
DataParser *sharedSingleton = [DataParser sharedInstance];
[self.copyOfSchedule removeAllObjects];
[self.copyOfSchedule addEntriesFromDictionary:sharedSingleton.schedule];
[self.tableView reloadData];
}
...
Но это не избавляет от ошибок EXC_BAD_ACCESS. Короче говоря: каков наилучший способ создания независимых копий объектов, определенных в одноэлементном объекте или делегате приложения и которые можно динамически обновлять по запросу? Так как я уже достаточно увлечен проектом и многое продолжается, я понимаю, что мой вопрос может быть немного неопределенным. Тем не менее, я надеюсь, что есть кто-то, кто мог бы как-то просветить меня.