Мой первый эксперимент с блоками дает мне EXC_BAD_ACCESS, и я понятия не имею, почему - PullRequest
0 голосов
/ 17 января 2012

- Здравствуйте, просто как говорится в названии. У меня есть класс загрузчика, который я хочу использовать, чтобы .. скачать вещи. Я думал, что я пытаюсь использовать блок, чтобы уведомить абонента, что загрузка завершена. Метод startWithRequest вызывается из одноэлементного класса, который обрабатывает веб-сервис .net. Я сохраняю completionBlock в переменной экземпляра, а затем вызываю ее позже, когда загрузка заканчивается. Там это дает мне EXC_BAD_ACCESS. Я пытался сохранить completionBlock, это не помогло. Вот код:

-(void) startWithRequest : (NSURLRequest *) request : (void (^)(NSData *data, NSError *error))_completionBlock {
  completionBlock = _completionBlock;
  if (working) {
    [self cancel];
  }
  working = TRUE;
  canceled = FALSE;

  [Globals ShowNetworkActivity];
  urlConnection = [[NSURLConnection alloc] initWithRequest: request delegate: self];
}

- (void) connection:(NSURLConnection *) connection didReceiveResponse:(NSURLResponse *)response
{
  [urlData setLength: 0];
}

- (void) connection:(NSURLConnection *) connection didReceiveData:(NSData *)data
{
  if (!urlData)
  {
    urlData = [[NSMutableData alloc] initWithCapacity: bufferSize];
  }
  [urlData appendData: data];
}

- (void) connectionDidFinishLoading:(NSURLConnection *)connection
{
  [Globals HideNetworkActivity];
  self.urlConnection = nil;
  ////////HERE it gives me the error
  if (!canceled) completionBlock(urlData, nil);
  self.urlData = nil;
  working = FALSE;
}

- (void) connection:(NSURLConnection *)connection didFailWithError:(NSError *)error
{
  [Globals HideNetworkActivity];
  self.urlConnection = nil;
  self.urlData = nil;

  if (!canceled) completionBlock(nil, error);
  working = FALSE;
}

-(void) cancel
{
  if (working) {
    canceled = TRUE;
    [urlConnection cancel];
    [Globals HideNetworkActivity];
    self.urlConnection = nil;
    self.urlData = nil;
    working = FALSE;
  }
}

Любая помощь приветствуется.

1 Ответ

4 голосов
/ 17 января 2012

Вам нужно скопировать блок, а не сохранять его.

Никакое сохранение не сохранит блок, который был создан в стеке, потому что его хранилище исчезнет, ​​как только выйдет функция, определенная в нем.

-(void) startWithRequest : (NSURLRequest *) request : (void (^)(NSData *data, NSError *error))_completionBlock {
    completionBlock = [_completionBlock copy];

// etc
...