[英]Wait for Asynchronous Operations in Objective-C
I'm googling like crazy and still confused about this. 我谷歌搜索疯狂,仍然对此感到困惑。
I want to download an array of file urls to disk, and I want to update my view based on the bytes loaded of each file as they download. 我想将一个文件URL数组下载到磁盘,我想根据下载时每个文件加载的字节更新我的视图。 I already have something that will download a file, and report progress and completion via blocks.
我已经有了下载文件的东西,并通过块报告进度和完成情况。
How can I do this for each file in the array? 如何为阵列中的每个文件执行此操作?
I'm ok doing them one at a time. 我可以一次做一个。 I can calculate the total progress easily that way:
我可以通过这种方式轻松计算总进度:
float progress = (numCompletedFiles + (currentDownloadedBytes / currentTotalBytes)) / totalFiles)
I mostly understand GCD and NSOperations, but how can you tell an operation or dispatch_async block to wait until a callback is called before being done? 我主要理解GCD和NSOperations,但是如何告诉操作或dispatch_async块在完成之前等待回调? It seems possible by overriding NSOperation, but that seems like overkill.
似乎有可能通过覆盖NSOperation,但这似乎有点矫枉过正。 Is there another way?
还有另外一种方法吗? Is it possible with just GCD?
只有GCD才有可能吗?
I'm not sure if I understand you correctly, but perhaps you need dispatch semaphores to achieve your goal. 我不确定我是否理解正确,但也许你需要派遣信号量来实现你的目标。 In one of my projects I use a dispatch semaphore to wait until another turn by another player is completed.
在我的一个项目中,我使用调度信号量等待另一个玩家完成另一个转弯。 This is partially the code I used.
这部分是我使用的代码。
for (int i = 0; i < _players.count; i++)
{
// a semaphore is used to prevent execution until the asynchronous task is completed ...
dispatch_semaphore_t sema = dispatch_semaphore_create(0);
// player chooses a card - once card is chosen, animate choice by moving card to center of board ...
[self.currentPlayer playCardWithPlayedCards:_currentTrick.cards trumpSuit:_trumpSuit completionHandler:^ (WSCard *card) {
BOOL success = [self.currentTrick addCard:card];
DLog(@"did add card to trick? %@", success ? @"YES" : @"NO");
NSString *message = [NSString stringWithFormat:@"Card played by %@", _currentPlayer.name];
[_messageView setMessage:message];
[self turnCard:card];
[self moveCardToCenter:card];
// send a signal that indicates that this asynchronous task is completed ...
dispatch_semaphore_signal(sema);
DLog(@"<<< signal dispatched >>>");
}];
// execution is halted, until a signal is received from another thread ...
DLog(@"<<< wait for signal >>>");
dispatch_semaphore_wait(sema, DISPATCH_TIME_FOREVER);
dispatch_release(sema);
DLog(@"<<< signal received >>>");
dispatch groups are the GCD facility designed to track completion of a set of independent or separately async'd blocks/tasks. 调度组是GCD工具,用于跟踪一组独立或单独异步的块/任务的完成情况。
Either use dispatch_group_async() to submit the blocks in question, or dispatch_group_enter() the group before triggering the asynchronous task and dispatch_group_leave() the group when the task has completed. 使用dispatch_group_async()提交有问题的块,或者在触发异步任务之前使用dispatch_group_enter()组,并在任务完成时使用dispatch_group_leave()组。
You can then either get notified asynchronously via dispatch_group_notify() when all blocks/tasks in the group have completed, or if you must, you can synchronously wait for completion with dispatch_group_wait(). 然后,当组中的所有块/任务完成时,您可以通过dispatch_group_notify()异步通知,或者如果必须,您可以使用dispatch_group_wait()同步等待完成。
I just wanted to note that I did get it working by subclassing NSOperation and making it a "concurrent" operation. 我只想注意,我确实通过继承NSOperation并使其成为“并发”操作来实现它。 (Concurrent in this context means an async operation that it should wait for before marking it as complete).
(此上下文中的并发意味着在将其标记为完成之前应等待的异步操作)。
http://www.dribin.org/dave/blog/archives/2009/05/05/concurrent_operations/ http://www.dribin.org/dave/blog/archives/2009/05/05/concurrent_operations/
Basically, you do the following in your subclass 基本上,您在子类中执行以下操作
start
to begin your operation start
开始您的操作 isConcurrent
to return YES
isConcurrent
返回YES
willChangeValueForKey:
and didChangeValueForKey:
for isFinished
and isExecuting
willChangeValueForKey:
和didChangeValueForKey:
for isFinished
and isExecuting
And in the class containing the queue 并在包含队列的类中
maxConcurrentOperationCount
on the NSOperationQueue
to 1
maxConcurrentOperationCount
上的NSOperationQueue
为1
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.