Общий источник данных Singleton в Objective-C - PullRequest
3 голосов
/ 10 декабря 2008

Привет, ребята - я пишу довольно простое приложение для iPhone. Данные поступают из plist-файла (в основном NSDictionary), который я пытаюсь загрузить в одноэлементный класс и использовать на разных контроллерах представления для доступа к данным.

Вот реализация для моего синглтона (в значительной степени смоделирована после этой темы )

@implementation SearchData

@synthesize searchDict;
@synthesize searchArray;

- (id)init {
    if (self = [super init]) {
        NSString *path = [[NSBundle mainBundle] bundlePath];
        NSString *finalPath = [path stringByAppendingPathComponent:@"searches.plist"];
        searchDict = [NSDictionary dictionaryWithContentsOfFile:finalPath];
        searchArray = [searchDict allKeys];
    }

    return self;
}

- (void)dealloc {
    [searchDict release];
    [searchArray release];
    [super dealloc];
}

static SearchData *sharedSingleton = NULL;

+ (SearchData *)sharedSearchData {
    @synchronized(self) {
        if (sharedSingleton == NULL)
            sharedSingleton = [[self alloc] init];
    }   
    return(sharedSingleton);
}

@end

Поэтому всякий раз, когда я пытаюсь получить доступ к свойствам searchDict или searchArray в другом месте моего приложения (например, делегат TableView), вот так:

[[[SearchData sharedSearchData] searchArray] objectAtIndex:indexPath.row]

Я получаю исключение, заявляющее *** - [NSCFSet objectAtIndex:]: нераспознанный селектор, отправленный экземпляру 0x5551f0

Я не совсем уверен, почему сообщение objectAtIndex отправляется объекту NSCFSet, я чувствую, что мой синглтон реализован неправильно или что-то в этом роде. Я также попробовал более сложную одноэлементную реализацию, подобную рекомендованной Apple в вышеупомянутом потоке , и у меня возникла та же проблема. Спасибо за любую информацию, которую вы можете предоставить.

Ответы [ 3 ]

11 голосов
/ 10 декабря 2008

В вашем методе -init вы напрямую обращаетесь к переменным вашего экземпляра и не сохраняете их. Они освобождаются, а их память используется другими объектами позже при жизни вашего приложения.

Либо сохраните созданные вами объекты, либо используйте некомфортные методы для их создания.

searchDict = [[NSDictionary alloc] initWithContentsOfFile:finalPath];
searchArray = [[searchDict allKeys] retain];
1 голос
/ 10 декабря 2008

Всякий раз, когда вы присваиваете синтезированные переменные, делайте это через 'self', поэтому:

- (id)init {
  if (self = [super init]) {
      NSString *path = [[NSBundle mainBundle] bundlePath];
      NSString *finalPath = [path stringByAppendingPathComponent:@"searches.plist"];
      self.searchDict = [NSDictionary dictionaryWithContentsOfFile:finalPath];
      self.searchArray = [searchDict allKeys];
  }

  return self;

}

Также убедитесь, что вы установили переменные, которые будут «сохраняться» в заголовочном файле.

0 голосов
/ 03 августа 2009

Привет, Можете ли вы сказать мне, в чем преимущество, когда мы присваиваем синтезированные переменные через 'self'? Спасибо Шива

значения устанавливаются через установщик; оно освобождает предыдущее значение и сохраняет то, которое вы присваиваете.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...