Работа с блоками, обработчиками завершения, dispatch_async vs dispatch_sync - PullRequest
4 голосов
/ 01 марта 2012

Я выполняю онлайн-извлечение данных в потоке и хочу сделать что-то сразу после выполнения блока.

Вот мой код:

- (IBAction)refresh:(UIBarButtonItem *)sender {
    NSLog(@"checking");
    [self editToolbar];
    dispatch_queue_t fetchQ = dispatch_queue_create("Refreshing", NULL);
    dispatch_async(fetchQ, ^{
        [self setupFetchedResultsController];
        [self fetchImonggoItemsDataIntoDocument: self.itemDatabase];
    });
    dispatch_release(fetchQ); 

    NSLog(@"done checking");
    //do something here
}

Дело в том, что dispatch_async немедленно возвращает данные и "готово к проверке" печатает немедленно, даже до завершения выполнения блока. Как мне это решить?

Ответы [ 2 ]

4 голосов
/ 04 марта 2012

Я думаю, что это архитектурная проблема.Задачи имеют что-то вроде:

  1. панель инструментов редактирования
  2. fetchImonggoItemsDataIntoDocument
  3. сделать что-то еще

Если это должно быть сделано точно в порядкетогда я не совсем понимаю использование блоков или очередей;просто запускайте операторы друг за другом, и вы будете установлены.

В противном случае альтернативой # 1 будет использование dispatch_sync вместо dispatch_async.Опять же, я не совсем уверен, какая польза от использования очереди, но она есть.

Альтернативой # 2 будет использование обратного вызова из блока.Что-то вроде:

- (IBAction)refresh:(UIBarButtonItem *)sender {
    NSLog(@"checking");
    [self editToolbar];
    dispatch_queue_t fetchQ = dispatch_queue_create("Refreshing", NULL);
    dispatch_async(fetchQ, ^{
        [self setupFetchedResultsController];
        [self fetchImonggoItemsDataIntoDocument: self.itemDatabase];
        [self doneChecking]; // <-- NOTE! call the callback
    });
    dispatch_release(fetchQ); 
}

// NOTE! refresh: has been split up into two methods
- (void)doneChecking:
    NSLog(@"done checking");
    //do something here
}
1 голос
/ 01 марта 2012

Как уже говорили другие, это, вероятно, то, что вам нужно.

NSArray *items = [iMonggoFetcher fetchImonggoData:IMONGGO_GENERIC_URL_FOR_PRODUCTS withFormat:@"json" withDateRangeArgs:args];
[document.managedObjectContext performBlock:^{
    for (NSDictionary *itemInfo in items){
        [Product productWithImonggoInfo:itemInfo inManagedObjectContext:document.managedObjectContext];
    }
    // Put here what you need :)
}];
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...