objective-c – 调度队列:如何判断它们是否正在运行以及如何阻止它们

objective-c – 调度队列:如何判断它们是否正在运行以及如何阻止它们,第1张

概述我只是玩GCD和我写了一个玩具CoinFlipper应用程序。 这里是翻转硬币的方法: - (void)flipCoins:(NSUInteger)nFlips{ // Create the queues for work dispatch_queue_t mainQueue = dispatch_get_main_queue(); dispatch_queue_t qu 我只是玩GCD和我写了一个玩具CoinFlipper应用程序。

这里是翻转硬币的方法:

- (voID)flipCoins:(NSUInteger)nFlips{    // Create the queues for work    dispatch_queue_t mainQueue = dispatch_get_main_queue();    dispatch_queue_t queue = dispatch_get_global_queue(disPATCH_QUEUE_PRIORITY_DEFAulT,NulL);    // Split the number of flips into whole chunks of kChunkSize and the remainder.    NSUInteger numberOfWholeChunks = nFlips / kChunkSize;    NSUInteger numberOfRemainingFlips = nFlips - numberOfWholeChunks * kChunkSize;    if (numberOfWholeChunks > 0) {        for (NSUInteger index = 0; index < numberOfWholeChunks; index++) {            dispatch_async(queue,^{                NSUInteger h = 0;                NSUInteger t = 0;                flipTheCoins(kChunkSize,&h,&t);                dispatch_async(mainQueue,^{                    self.nheads += h;                    self.nTails += t;                });            });        }    }    if (numberOfRemainingFlips > 0) {        dispatch_async(queue,^{            NSUInteger h = 0;            NSUInteger t = 0;            flipTheCoins(numberOfRemainingFlips,&t);            dispatch_async(mainQueue,^{                self.nheads += h;                self.nTails += t;            });        });    }}

如你看到的;我打破翻转的数量大块,在后台翻转他们和更新主队列中的属性。窗口控制器正在观察属性,并使用运行结果更新UI。

我已经看过了并发编程指南和GCD文档,虽然有一种方法来暂停一个队列,没有办法阻止它们,并删除所有排队和不运行的对象。

我想能够连接一个“停止”按钮取消翻转一旦它开始。使用NSOperationQueue我可以观察operationCount属性知道它是否正在运行,而cancelAllOperations可以删除排队的块。

我已经看过了并发编程指南和GCD文档,虽然有一种方法来暂停一个队列,没有办法阻止它们,并删除所有排队和不运行的对象。

所以: –

>如何判断我添加到队列中的块是否仍在等待?
>如何取消尚未运行的块?
>我是新来的GCD的东西,所以我做的对吗?

解决方法 这是使用GCD编程时的一个半常见问题。

简短的回答是GCD没有队列的取消API。理由:

>内存管理将变得非常复杂,因为给定的块可能负责释放给定的内存分配。通过总是运行块,GCD确保内存管理容易。
>实际上不可能在不破坏状态的情况下停止正在运行的块。
>大多数需要取消逻辑的代码已经在私有数据结构中跟踪该状态。

鉴于所有这些情况,它是更有效和强大的写如下代码:

dispatch_async(my_obj->queue,^{    bool done = false;    // do_full_update() takes too long,therefore:    while ( !my_obj->cancelled && !done ) {        done = do_partial_update(my_obj);    }});

哦,要知道队列是否已经完成了所有入队块的运行,您的代码可以简单地使用同步API执行一个空块:

dispatch_sync(my_obj->queue,^{});

正如评论中提到的,一个更好的方式来知道你的工作完成时间是使用调度组。将所有块分派给组,然后可以向组中添加完成处理程序。一旦工作完成,完成块将运行。

dispatch_group_t myGroup = dispatch_group_create();dispatch_group_async(myGroup,my_obj->queue,^{    bool done = false;    while ( !my_obj->cancelled && !done ) {        done = do_partial_update(my_obj);    }});dispatch_group_notify(myGroup,^{    NSLog(@"Work is done!");    dispatch_release(myGroup);});

所有块完成后,组将为空并触发通知块。从那里,您可以更新UI等。

祝好运并玩得开心点!

总结

以上是内存溢出为你收集整理的objective-c – 调度队列:如何判断它们是否正在运行以及如何阻止它们全部内容,希望文章能够帮你解决objective-c – 调度队列:如何判断它们是否正在运行以及如何阻止它们所遇到的程序开发问题。

如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。

欢迎分享,转载请注明来源:内存溢出

原文地址: https://outofmemory.cn/web/1042672.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-05-24
下一篇 2022-05-24

发表评论

登录后才能评论

评论列表(0条)

保存