1

ブロックを使った作業を始めたばかりです...非常に混乱しています。次のようなブロックを使用しています。

-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
NSDictionary *myDictionary = [[mySingleton arrayPeopleAroundMe] objectAtIndex:indexPath.row];

NSMutableString *myString = [[NSMutableString alloc] initWithString:@"http://www.domain.com/4DACTION/PP_profileDetail/"];
[myString appendString:[myDictionary objectForKey:@"userID"]];
NSURLRequest *urlRequest = [NSURLRequest requestWithURL:[NSURL URLWithString:[myString stringByAddingPercentEscapesUsingEncoding: NSUTF8StringEncoding]]
                                            cachePolicy:NSURLRequestUseProtocolCachePolicy
                                        timeoutInterval:60.0];
NSOperationQueue *queue = [[NSOperationQueue alloc] init];
[NSURLConnection
 sendAsynchronousRequest:urlRequest
 queue:queue
 completionHandler: ^( NSURLResponse *response,
                      NSData *data,
                      NSError *error)
 {
     [[mySingleton dictionaryUserDetail] removeAllObjects];
     [[mySingleton arrayUserDetail] removeAllObjects];

     if ([data length] > 0 && error == nil) // no error and received data back
     {
         NSError* error;
         NSDictionary *myDic = [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:&error];
         [mySingleton setDictionaryUserDetail:[myDic mutableCopy]];

         NSArray *myArray = [myDic objectForKey:@"searchResults"];
         [mySingleton setArrayUserDetail:[myArray mutableCopy]];

         [self userDetailComplete];
     } else if
         ([data length] == 0 && error == nil) // no error and did not receive data back
     {
         [self serverError];
     } else if
         (error != nil) // error
     {
         [self serverError];
     }
 }];
}

接続が完了すると、これが呼び出されます。

-(void)userDetailComplete {
ViewProfile *vpVC = [[ViewProfile alloc] init];
[vpVC setPassedInstructions:@"ViewDetail"];
[[self navigationController] pushViewController:vpVC animated:YES];
}

「メイン スレッドまたは Web スレッド以外のスレッドから Web ロックを取得しようとしました。これは、セカンダリ スレッドから UIKit を呼び出した結果である可能性があります。」エラーを取り除く唯一の方法は、userDetailComplete を次のように変更することでした。

-(void)userDetailComplete {
dispatch_async(dispatch_get_main_queue(), ^{
ViewProfile *vpVC = [[ViewProfile alloc] init];
[vpVC setPassedInstructions:@"ViewDetail"];
[[self navigationController] pushViewController:vpVC animated:YES];
});
}

私の質問: ブロックが使用されるたびに新しいスレッドが自動的に開始されますか? ブロックを使用する際に注意すべきその他の落とし穴はありますか?

4

1 に答える 1

7

ブロックはスレッドを作成しません。それらは閉鎖です。それらには、将来のある時点で実行できる実行可能なコードが含まれているだけです。

これはバックグラウンド スレッドで実行されています。

NSOperationQueue *queue = [[NSOperationQueue alloc] init];
[NSURLConnection
  sendAsynchronousRequest:urlRequest
  queue:queue
  ...

あなたは新しいキューを作成し、NSURLConnectionそのキューで折り返し電話するように依頼しました。メインスレッドでコールバックしたい場合は、 を渡し[NSOperationQueue mainQueue]ます。それは通常あなたが望むものです。

于 2013-04-05T22:03:34.993 に答える