Как да направите тази функция за блокиране на обратно извикване?

for (NSObject *aObj in myObjectArray) {
   [self doSomething:aObj
      completion:^{
      //Execute next aObj
   }];
}

Ето един прост входен цикъл, който изважда NSObject, след което ще вземе aObj, за да премине към doSomething, но doSomething има параметър, който е завършване, което е блок... Проблемът, който имам е....Следващият aObj трябва да бъде извикан, преди предишният aObj да е завършен. И след като всичко aObj е завършено в myObjectArray е завършено. Ще свърши. Но какво трябва да напиша в блоковете за завършване? объркан съм.

Симулиране на костюм:

  1. Ако myObjectArray има следващото aObj
  2. myObjectArray вземете aObj
  3. self се обажда doSomething
  4. когато selfdoSomething` приключи, кодът за завършване ще бъде изпълнен, обратно към стъпка 1.

person DNB5brims    schedule 30.11.2013    source източник


Отговори (2)


Не беше ясно (до коментара ви за отговора на DrummerB), че наистина искате последователна операция, а не едновременна -- не е нормално цикълът да се използва за последователна работа, но в различна нишка (въпреки че предполагам, че искате да излезете основната нишка за вашата тежка обработка).

Можете да постигнете това с помощта на NSOperationQueue:

NSOperationQueue *queue = [[NSOperationQueue alloc] init];
for (__block NSObject *aObj in myObjectArray) {
    [queue addOperationWithBlock:^{
        [self doSomething:aObj
            completion:^{
               // nothing special here, since we wait after the operation is queued
             }];
    }];
    [queue waitUntilAllOperationsAreFinished];
}

Имайте предвид, че добавих ключовата дума __block към aObj -- потенциално необходима, тъй като предавате това в блок.

person mah    schedule 30.11.2013

NSArray има метод enumerateObjectsWithOptions:usingBlock:, който ви позволява да посочите опция за изпълнение на блока за всеки обект едновременно. Може би това е, което търсите.

[array enumerateObjectsWithOptions:NSEnumerationConcurrent 
                        usingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
    [self doSomething:obj];
    // completion
}];
person DrummerB    schedule 30.11.2013
comment
Сладка! Работех върху прост (?) NSOperationQueue пример, но тъй като NSArray го обработва, нещата са много по-хубави по този начин! - person mah; 30.11.2013
comment
Но проблемът, който имам е ... следващият aObj ТРЯБВА да се нуждае от предишния aObj е завършен, което ще извика обратно блока за завършване. Актуализирам въпроса, за да изясня въпроса си. - person DNB5brims; 30.11.2013