Ios 如何检查全局调度队列是否为空?
在我的应用程序中,我使用全局调度队列和gcd来实现我的互联网网络。 我想在有网络活动时将网络指示器设置为可见 这是我的网络块->Ios 如何检查全局调度队列是否为空?,ios,objective-c-blocks,grand-central-dispatch,uiapplication,Ios,Objective C Blocks,Grand Central Dispatch,Uiapplication,在我的应用程序中,我使用全局调度队列和gcd来实现我的互联网网络。 我想在有网络活动时将网络指示器设置为可见 这是我的网络块-> { [[UIApplication sharedApplication]setNetworkActivityIndicatorVisible:YES]; send sync http request [[UIApplication sharedApplication]setNetworkActivityIndicatorVisible:NO]; } 我的问题
{
[[UIApplication sharedApplication]setNetworkActivityIndicatorVisible:YES];
send sync http request
[[UIApplication sharedApplication]setNetworkActivityIndicatorVisible:NO];
}
我的问题是:
一种可能的方法是创建一组任务,然后等待它们完成。在开始和结束之间,您可以更新活动指示器。显然,您需要一些对象来保留对组的引用。根据apple文档检查此代码:
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0); // Retain this queue somewhere accessible from the places you want to dispatch
dispatch_group_t group = dispatch_group_create(); // Retain this group somewhere accessible from the places you want to dispatch
// Add a task to the group
dispatch_group_async(group, queue, ^{
// Some asynchronous work
});
// Do some other work while the tasks execute.
disptach_sync(dispatch_get_main_queue(), ^{
[[UIApplication sharedApplication]setNetworkActivityIndicatorVisible:YES];
}
// When you cannot make any more forward progress,
// wait on the group to block the current thread.
dispatch_group_wait(group, DISPATCH_TIME_FOREVER);
// Release the group when it is no longer needed.
disptach_sync(dispatch_get_main_queue(), ^{
[[UIApplication sharedApplication]setNetworkActivityIndicatorVisible:NO];
}
dispatch_release(group);
请记住,您可以使用一个单例对象来分派块并跟踪等待。@DavidBemerguy的方法是一个很好的开始,但您通常希望使用
dispatch\u group\u notify
来实现它,以隐藏指示器。也就是说,依我看,这里不需要GCD。您只需要一个网络指示器控制器
创建侦听通知的对象(控制器),如DidStartNetworkActivity
和DidStopNetworkActivity
。启动或停止时发布通知。在控制器内部,保持计数,当它达到0时,隐藏指示器。类似这样的内容(完全未经测试,只需在此处键入,过去几天我一直在用Swift独家写作,请原谅任何缺少的分号):
.h:
m
@接口网络指示器控制器()
@属性(非原子、读写、赋值)NSInteger计数;
@结束
@实现网络指示器控制器
-(无效)开始{
NSNotificationCenter*nc=[NSNotificationCenter defaultCenter];
[nc addObserver:self name:DidStartNetworkActivityNotification选择器:@selector(didStart:)对象:nil];
[nc addObserver:自身名称:DidStopNetworkActivityNotification选择器:@selector(didStop:)对象:nil];
self.count=0;
}
-(无效)停止{
NSNotificationCenter*nc=[NSNotificationCenter defaultCenter];
[nc removeObserver:自身名称:DidStartNetworkActivityNotification对象:nil];
[nc removeObserver:自身名称:DidStopNetworkActivityNotification对象:nil];
}
-(无效)didStart:(NSNOTITION*)注释{
dispatch\u async(dispatch\u get\u main\u queue(){
self.count=self.count+1;
[[UIApplication sharedApplication]设置网络活动指示器可见:是];
});
}
-(无效)didStop:(NSNOTITITION*)注释{
dispatch\u async(dispatch\u get\u main\u queue(){
self.count=self.count-1;
如果(self.count问题#1的答案很简单,如果您更高一级并使用NSOperationQueue。向其提交块实际上并不比GCD困难,它可以让您更好地控制操作。@PhillipMills谢谢,我将检查documentation@PhillipMills但是第二个问题呢?我不知道,我更喜欢我对我实际使用过的东西发表了评论。:@PhillipMills谢谢你这是正确的方式。就我所知,记录在案的是,(至少目前是这样)没有用于确定任意GCD队列是否为空的公共API。即使您可以询问队列是否为空,也没有用,因为从您检查到您对其采取措施期间,队列可能不再为空。更糟糕的是,其他队列可能会以此队列为目标,并可以更改其目标队列。问题是如果针对某个队列的某些队列被挂起但有阻塞,则该队列是否为空。您可以通过调度组解决所有这些问题,但您必须决定您想要的答案是什么,这可能需要大量工作:Dell说,Rob。说得好。:)
extern NSString * const DidStartNetworkActivityNotification;
extern NSString * const DidStopNetworkActivityNotification;
@interface NetworkIndicatorController
- (void) start;
- (void) stop;
@end
@interface NetworkIndicatorController ()
@property (nonatomic, readwrite, assign) NSInteger count;
@end
@implementation NetworkIndicatorController
- (void)start {
NSNotificationCenter *nc = [NSNotificationCenter defaultCenter];
[nc addObserver:self name:DidStartNetworkActivityNotification selector:@selector(didStart:) object:nil];
[nc addObserver:self name:DidStopNetworkActivityNotification selector:@selector(didStop:) object:nil];
self.count = 0;
}
- (void)stop {
NSNotificationCenter *nc = [NSNotificationCenter defaultCenter];
[nc removeObserver:self name:DidStartNetworkActivityNotification object:nil];
[nc removeObserver:self name:DidStopNetworkActivityNotification object:nil];
}
- (void)didStart:(NSNotification *)note {
dispatch_async(dispatch_get_main_queue(), {
self.count = self.count + 1;
[[UIApplication sharedApplication]setNetworkActivityIndicatorVisible:YES];
});
}
- (void)didStop:(NSNotification *)note {
dispatch_async(dispatch_get_main_queue(), {
self.count = self.count - 1;
if (self.count <= 0) {
[[UIApplication sharedApplication]setNetworkActivityIndicatorVisible:NO];
}
});
}