1

ディスクから読み取るタスクがあり、かなり時間がかかる可能性があるため、メインスレッドで実行したくありません。ディスクから読み取った後に関数Xを呼び出す必要があります。iOSでこれを行うための最良の方法は何ですか?

これまでのところ、これは私が試したことです:

 NSInvocationOperation *processDataOperation = [[NSInvocationOperation alloc] initWithTarget:self selector:@selector(readDisk:) object:nil];
                [processDataOperation setQueuePriority:NSOperationQueuePriorityVeryHigh];
                [processDataOperation setCompletionBlock:^(void){
                     NSMutableArray *feedItemsArray = [self generateFeedItemsFromDictionary:streamDiskData];
                     [self postFetchCompletedNotificationForDict:queryStringDict withFeedItems:feedItemsArray isFresh:NO];
                }];

基本的に私はNSInvocationOperationを使用していて、それを完了ブロックに設定していますが、問題は、完了ブロックでreadDiskで生成された結果が必要なことです。完了ブロックでそれにアクセスするにはどうすればよいですか?それはほとんど不可能ですよね?

4

2 に答える 2

7

NSInvocations を使用すると、必要以上に複雑になりますが、メイン スレッドを超えたわずかな量の作業を行うことができます。

GCD と NSOperations の両方を使用して、さまざまな同時実行戦略を実装できます。オブジェクト指向の観点から見ると、NSOperations は CGD ブロックよりも高度に抽象化されているため、(imo) "設計" が容易になり、実装している範囲を超えて最適化される可能性があります。GCD は低レベルです: これにより、GCD とのやり取りが少し複雑に見えます (実際にはそうではありません)。

私の個人的なアプローチは、アプリケーションで設計/オーケストレーションされた同時実行パターンがあるシナリオで NSOperations を使用し、単純な同時実行/バックグラウンド操作には GCD を使用することです。

設計に関係なく、バックグラウンドで実行する必要がある任意のタスクを起動するだけでよい場合は、CGD を使用します。それは私がおそらくこの場合に使用するものです:

dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_BACKGROUND, 0), ^{

    [self readDisk];
    NSMutableArray *feedItemsArray = [weakSelf generateFeedItemsFromDictionary:streamDiskData];

        dispatch_sync(dispatch_get_main_queue(), ^{

        //Call back to the main thread before performing/posting anything touching UIKit
        [self postFetchCompletedNotificationForDict:queryStringDict withFeedItems:feedItemsArray isFresh:NO];
        })
})];
于 2012-06-22T00:40:04.453 に答える
0

代わりに、いつでもグランド セントラル ディスパッチを使用してバックグラウンドで操作を実行できます。

これはブロックなので、通常どおりメソッドを呼び出して結果を保存できます。次に、UI を更新する必要がある場合、または完了後に必要なことを行う必要がある場合は、メイン キューを取得します。

dispatch_queue_t queue = dispatch_queue_create("read disc", NULL);
dispatch_async(queue, ^{
    result = [self readDisc];
    dispatch_async(dispatch_get_main_queue(), ^{
        //update UI or do whatever you need to do with the result of readDisc
    });
});
dispatch_release(queue);
于 2012-06-21T23:24:20.597 に答える