1

ここに私の懸念があります: 何らかの理由で、3 つの異なる Web 要求結果からの回答を取得してグループ化する必要があります。そのうちの 3 つが戻ってきたら、completionBlock を呼び出してすべての結果を渡す必要があります。NSOperation API を使用して、次のようなことができました。

Session * session = [[ServiceLocator sharedInstance] serviceForName:ServiceLocatorNameUserRepository];


NSString * urlMethod = @"POST";
NSDictionary * params = @{kParkadomWebServiceUser : session.currentUser.userID};

NSMutableDictionary * records = [NSMutableDictionary new];

NSOperation * currentBooking = [self performRequestWithPath:API_BOOKING_INPROGRESS
                                                         method:urlMethod
                                                      parameter:params
                                                     completion:^(id json, NSError * error)
                                                     {
                                                         records[@"current"] = error ? error : json;

                                                     }];

NSOperation * upcomingBookings = [self performRequestWithPath:API_BOOKING_UPCOMING
                                                         method:urlMethod
                                                      parameter:params
                                                     completion:^(id json, NSError * error)
                                                     {
                                                         records[@"upcoming"] = error ? error : json;

                                                     }];

NSOperation * pastBookings = [self performRequestWithPath:API_BOOKING_HISTORY
                                                   method:urlMethod
                                                parameter:params
                                               completion:^(id json, NSError * error)
                                               {
                                                   records[@"past"] = error ? error : json;

                                               }];


NSBlockOperation * completionOperation = [NSBlockOperation blockOperationWithBlock:^{
    completion([records copy], nil);
}];
[completionOperation addDependency:currentBooking];
[completionOperation addDependency:upcomingBookings];
[completionOperation addDependency:pastBookings];

[[NSOperationQueue mainQueue] addOperation:completionOperation];

ここで、completed は明らかに、エントリ パラメータとして指定された補完ブロックです。performRequestWithPath:method:parameter:completion: NSOperation を作成し、それをグローバル キューに追加して返すので、ここに 3 つの Web 呼び出しがあります。次に、ブロック操作を作成し、3 つ前のブロックに依存関係を追加して、3 つのブロックが完了する前に起動されないようにします。

私の懸念は、NSMutableArray に関するものです。このようなことを行うのは貧弱な設計のように思えます.2つの呼び出しがまったく同時に終了した場合に本当にバグプルーフであるかどうかはわかりません. (私は、完了ブロックがメイン キューで呼び出されることを perform...: メソッドで確認したことに注意してください)。

フィードバックはありますか?提案、批判、理論...私はすべてオープンです:)

4

2 に答える 2

1

同期を追加する必要があります。

@synchronized(myArray) {
  [myArray doSomething];
}

たとえば、コードでは次のようになります。

@synchronized(records) {
    records[@"past"] = error ? error : json;
}

編集:@ gnasher729は、完了ブロックがメインスレッドで実行される場合、同期の必要がないという良い点をもたらします。

于 2014-12-12T13:58:14.020 に答える