Дождитесь завершения операции асинхронной задачи и продолжите текущую асинхронную задачу.

У меня есть два метода, которые запускают свой код в фоновом режиме, и метод1 запускает метод2 следующим образом:

+(void)insertAllDataInDatabase{
    NSLog(@"1");        
    NSString *url=@"http://localhost/kalimat/get_all_artists.php";        
    //NSLog(@"url %@",url);        
    NSURL *urlChannels= [ NSURL URLWithString:url];                
    NSURLRequest *request = [NSURLRequest requestWithURL:urlChannels];                
    AFJSONRequestOperation *operation = [AFJSONRequestOperation 
        JSONRequestOperationWithRequest:request 
                                success:^(NSURLRequest *request, 
                                          NSHTTPURLResponse *response, 
                                          id JSON) {
        dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^(void) 
        {
            NSMutableArray *arrayOfJson=JSON;
            for (int i=0; i<[arrayOfJson count]; i++) {
                NSLog(@"2");
                NSMutableDictionary *songDico=[arrayOfJson objectAtIndex:i];
                NSString *artist=[songDico objectForKey:@"artist"];
                [self getArtistSongs:artist];
            }
        });
        NSLog(@"6");

    } failure:^(NSURLRequest *request, NSHTTPURLResponse *response,
                NSError *error, id JSON) {
        //DLog(@"Request Failure Because %@",[error userInfo]);
    }];
    [operation start];
}

+(void)getArtistSongs:(NSString*)artist {
    NSLog(@"3");
    LKDBHelper* globalHelper = [LKDBHelper getUsingLKDBHelper];
    NSMutableArray *arrayOfSongs=[[NSMutableArray alloc]init];
    artist = [artist stringByReplacingPercentEscapesUsingEncoding:NSUTF8StringEncoding];
    dispatch_async(dispatch_get_global_queue( DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^(void){
        //DLog(@"artisttt %@",artist);
        NSString *url=[NSString stringWithFormat:@"%@?artist=%@", @"http://localhost/kalimat/get_kalimat.php",artist];
        url = [url stringByAddingPercentEncodingWithAllowedCharacters:NSCharacterSet.URLQueryAllowedCharacterSet];
        //NSLog(@"url %@",url);
        NSURL *urlChannels= [ NSURL URLWithString:url];
        NSURLRequest *request = [NSURLRequest requestWithURL:urlChannels];
        [LKDBHelper clearTableData:[Song class]];
        AFJSONRequestOperation *operation =
        [AFJSONRequestOperation JSONRequestOperationWithRequest:request
            success:^(NSURLRequest *request,
                      NSHTTPURLResponse *response,
                      id JSON) {
                NSMutableArray *arrayOfJson=JSON;
                for (int i=0; i<[arrayOfJson count]; i++) {
                    NSLog(@"4");
                    NSMutableDictionary *songDico=[arrayOfJson objectAtIndex:i];
                    DCKeyValueObjectMapping *parser = [DCKeyValueObjectMapping mapperForClass: [Song class]];
                    Song *song = [parser parseDictionary:songDico];
                    song.artist=artist;
                    [arrayOfSongs addObject:song];
                    //DLog(@"inserting...");
                    [globalHelper insertToDB:song];
                    //DLog(@"getting lyrics");
                    //[self getLyricsWhereArtist:artist andSong:song.song];
                    //[[NSNotificationCenter defaultCenter] postNotificationName:@"AllArtistsSongs" object:arrayOfSongs];
                }
                NSLog(@"5");
            } failure:^(NSURLRequest *request, NSHTTPURLResponse *response,
                        NSError *error, id JSON) {
                DLog(@"Request Failure Because %@",[error userInfo]);
            }];
        [operation start];
    });
}

Основываясь на NSLogs, я хочу иметь:

1
2
3
4
4
4
4
...
5
6

Но у меня есть:

1
6
2
3
2
3
2
3
2
3
...

Есть ли способ заказать выполнение этих методов? Большое спасибо за Вашу помощь.


person androniennn    schedule 31.03.2014    source источник


Ответы (1)


Вы уже звоните getArtistSongs: из фонового потока. Если вы хотите, чтобы они запускались последовательно, просто удалите вызов dispatch_async из этого метода. Вам также нужно будет выполнять эти запросы синхронно; Я не использовал AFNetworking, поэтому не знаю, доступен ли он и как это сделать.

Это будет работать без блокировки основного потока, потому что ваши вызовы getArtistSongs: исходят из блока, работающего в фоновом потоке:

dispatch_async(dispatch_get_global_queue( DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^(void){

    // All this code runs in the background.

    NSMutableArray *arrayOfJson=JSON;
    for (int i=0; i<[arrayOfJson count]; i++) {

        NSLog(@"2");

        NSMutableDictionary *songDico=[arrayOfJson objectAtIndex:i];
        NSString *artist=[songDico objectForKey:@"artist"];

        [self getArtistSongs:artist];
    }

    // All code above runs in the background.

});

6, конечно, по-прежнему будет печататься сразу после 1. Если вам нужен код для запуска в последнюю очередь, он идет внутри блока после цикла for songDiscos, возможно, завернутый в dispatch_async в основной поток.

person dokkaebi    schedule 31.03.2014
comment
Но синхронное выполнение операции заблокирует почтовый поток, и я хочу, чтобы этот процесс выполнялся в фоновом режиме. - person androniennn; 31.03.2014
comment
Смотрите мою правку. Запросы будут выполняться синхронно в фоновом потоке, а основной поток будет продолжать работать. - person dokkaebi; 31.03.2014
comment
Теперь у меня другой вывод: 1,6,2,3,2,3,2,3...4,2,3,4,2,3... я не понимаю эту часть 2,3. Почему это не выполняется, как 2,3,4,4,4,4,...,5 - person androniennn; 31.03.2014
comment
Я ожидаю 1,6,2,3,4,4,4,4,5,2,3,4,4,4,5,2,3,4,4,4,5.... Я не понимаю ваших 4,2,3,4,2,3 ... но я думаю, что наиболее вероятно (и 16232323 предполагает), что запросы songDisco все еще асинхронны. Может быть, вы переключили неправильный запрос на синхронный? Я думаю, что на данный момент имеет смысл отредактировать вопрос с вашим обновленным кодом. - person dokkaebi; 01.04.2014