Лучшие практики, запускать и забывать асинхронные классы? - PullRequest
1 голос
/ 10 апреля 2011

У меня есть класс, единственная цель которого - загрузить определенный файл из сети, сохранить его локально, а затем вернуть локальный путь к сохраненному файлу.

Я использую этот класс в зависимости от того, есть ли у меня локальная копия рассматриваемого файла или нет, и я иногда вызываю его несколько раз одновременно, если требуется загрузить более одного файла. То, как я использую это просто

Loader *l = [[Loader alloc] initWithDelegate:self];
[l downloadFile:someFile];
[l release];

Дело в том, что для того, чтобы сохранить его, пока он не закончил загрузку, я на самом деле делаю [self retain]; в классе, затем [self autorelease];, когда это будет сделано. Это кажется хакерским. Как люди справляются с этим?

Ответы [ 2 ]

1 голос
/ 10 апреля 2011

В этих обстоятельствах я думаю, что ваш загрузчик может сохранить и автоматически выпустить сам себя. Наиболее целесообразным решением может быть просто добавить подробный комментарий к вашему коду, который объясняет, почему он делает то, что делает. Самая большая проблема в том, что Loader принимает делегата. Делегаты обычно не сохраняют своих делегатов, чтобы избежать циклов сохранения, но в этом случае кажется возможным, что делегат мог быть освобожден до того, как Загрузчик завершит загрузку своего файла. Если это произойдет, вероятен сбой. Поэтому, если вы хотите продолжить использовать этот стиль «забей и забудь», возможно, вы захотите, чтобы Loader сохранил свой делегат.

1 голос
/ 10 апреля 2011

Я согласен, что [self release] и [self autorelease] чувствуют себя странно, но это не значит, что они не правы .В некоторых ситуациях они могут быть правильными для использования (и я использовал их раньше).

Однако, если вы хотите избежать их, вы можете создать класс LoaderManager, который просто владеетLoader объектов, пока они не закончили загружать вещи.По сути, это будет обертка вокруг массива, и вы будете использовать ее следующим образом (или что-то в этом роде):

@interface LoaderManager : NSObject {
  NSMutableSet *loaders;
}
@end
@implementation LoaderManager
- (id)init {
  self = [super init];
  if (self) {
    loaders = [[NSMutableSet alloc] init];
  }
  return self;
}
- (void)dealloc {
  [loaders release];
  [super dealloc];
}
- (void)addLoader:(Loader *)loader {
  [loaders addObject:loader];
}
@end

И тогда ваш Loader объект сделает:1015 * Что внутренне просто вызовет:

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