ios - 利用afnetworking3.0通过for循环发送请求,如何保证接收到数据的顺序和发送请求的顺序一致?
巴扎黑
巴扎黑 2017-04-17 17:51:04
0
4
422

利用AFN3.0进行网络请求,要发送的参数在一个数组里,每次取数组中的一条数据设置参数发送请求,

我通过for循环遍历数组并设置参数发送请求,将网络请求返回的数据添加到一个新的数组中,

发现不是每次请求返回的数据的顺序是一样的,功能需求返回数据的排序必须跟发送请求的顺序是一样的,

求问有什么方法保证前一次请求返回数据之后再发送下一次请求?

非常感谢,万分感谢!!!!

/**
 *  加载订单数据,设置控件位置
 */
- (void)loadOrderData {
        NSString *userID = [[NSUserDefaults standardUserDefaults] stringForKey:@"GOId"];
        NSDictionary *dict = @{
                               @"GOId" : userID,
                               };
        // 将字典转为json
        NSDictionary *params = [ELHOCToJson ocToJson:dict];
        
        NSString *URL = [NSString stringWithFormat:@"%@RealtimeOrder_getROListCon12345.action", ELHBaseURL];
        
        
        __weak typeof(self) weakSelf = self;
        [self.manager POST:URL parameters:params progress:nil success:^(NSURLSessionDataTask * _Nonnull task, id  _Nullable responseObject) {
            
            weakSelf.ELHOrderArray = [ELHOrderModel mj_objectArrayWithKeyValuesArray:responseObject];
            

            
            // 获取订单编号
            for (int i = 0; i < weakSelf.ELHOrderArray.count; i++) {
                ELHOrderModel *model = weakSelf.ELHOrderArray[i];
                
                [weakSelf.ELHOrderNumArray addObject:model.ROBM];
                
            }
            

            // 根据获取到的订单编号加载订单详情列表
            if (weakSelf.ELHOrderNumArray != nil) {
                dispatch_queue_t conCurrentQueue = dispatch_queue_create("order", NULL);
                for (NSString *ROBM in weakSelf.ELHOrderNumArray) {
                    dispatch_barrier_async(conCurrentQueue, ^{
                        // 加载订单详情列表
                        [self loadOrderDetailData:ROBM];
                    });
                }
            }
            
            
       
            
            // 刷新数据
            [orderVC.tableView reloadData];
            
        } failure:^(NSURLSessionDataTask * _Nullable task, NSError * _Nonnull error) {
            NSLog(@"%@", error);
        }];
    
}



/**
 *   加载订单详情列表
 */
- (void)loadOrderDetailData:(NSString *)ROBM {
    NSDictionary *dict = @{
                           @"ROBM" : ROBM,
                           };
    
    // 字典转json
    NSDictionary *params = [ELHOCToJson ocToJson:dict];
    
    NSString *URL = [NSString stringWithFormat:@"%@OrderPrice_getOPListByROBM.action", ELHBaseURL];
    
    __weak typeof(self) weakSelf = self;
    [self.manager POST:URL parameters:params progress:nil success:^(NSURLSessionDataTask * _Nonnull task, id  _Nullable responseObject) {       
    
        // 将获取到的订单详情数据逐个添加到数组中
        [weakSelf.ELHOrderDetailArray addObject:[ELHOrderDetailModel mj_objectArrayWithKeyValuesArray:responseObject]];
        ELHOrderTableViewController *orderVC = weakSelf.childViewControllers.firstObject;
        
        orderVC.orderDetailArray = weakSelf.ELHOrderDetailArray;
        
        // 刷新数据
        [orderVC.tableView reloadData];
    } failure:^(NSURLSessionDataTask * _Nullable task, NSError * _Nonnull error) {
        NSLog(@"%@", error);
    }];
}
巴扎黑
巴扎黑

全部回覆(4)
巴扎黑

按你的做法當然不一定一樣了,有些請求可能是後發出的,但返回比較快,就先返回了。

不清楚你的需求是不是一定要依序請求。例如像一次上傳 10 張圖片,然後把回傳的 url 依序塞到一個陣列裡這種需求,我們通常都是分幾個執行緒同時請求的,而不是一張一張依序傳的。這樣快很多。

如果你是要保證依序請求的話,就要把下一次請求的發送放在上次請求結束之後。如:

- (void)requestWithArray:(NSArray*)array index:(NSInteger)index completion:(SomeBlock)completion {
    if (index >= array.count) {
        if (completion) {
            completion();
        }
        return;
    }
    
    AFHTTPRequestOperationManager* manager = [self httpsRequestManager];
    NSDictionary* params = @{"key":array[index]};
    __weak typeof(self) weakSelf = self;
    [manager GET:url parameters:params success:^(AFHTTPRequestOperation *operation, id responseObject) {
        [weakSelf requestWithArray:array index:index + 1 completion:completion];
    } failure:^(AFHTTPRequestOperation *operation, NSError *error) {
        // handle failure
    }];

大概是這意思,懂了嗎?

但是像上傳 10 張圖片那種,就是只要保證結果順序正確,不需要請求一個一個串行的話,應該用[AFURLConnectionOperation batchOfRequestOperations:]。最好優先考慮下這樣是否能滿足你的需求。

洪涛

你的問題類似這個 https://segmentfault.com/q/1010000004632... 如果你只是希望保證回傳結果的順序,就不一定需要所有的請求串列的進行。

另外,如果你非要串列的進行請求的話,可以新建一個 NSOperationQueue,並把它的 maxConcurrentOperationCount 設定為 1, 然後把你的每個請求順序地加入到這個 NSOperationQueue 裡去。

PHPzhong

使用GCD dispatch_barrier_async 這個方法可以,但是佇列必須是自己建立的,而不能是全域佇列

dispatch_queue_t conCurrentQueue = dispatch_queue_create("test", NULL);
NSArray *numAry = @[@"1",@"3",@"4",@"2",];

for (NSString *str in numAry) {
    
        dispatch_barrier_async(conCurrentQueue, ^{
            
            //这里写网络请求
        });
}
Ty80

新寫了一個輔助類,希望可以幫助你。
https://github.com/sunbohong/SunOrderArr...

熱門教學
更多>
最新下載
更多>
網站特效
網站源碼
網站素材
前端模板