【发布时间】:2011-03-23 14:31:59
【问题描述】:
我的 iOS 应用中有一个异步服务器请求:
[self performSelectorInBackground:@selector(doSomething) withObject:nil];
如何检测到此操作的结束?
【问题讨论】:
标签: iphone multithreading ios detect nsthread
我的 iOS 应用中有一个异步服务器请求:
[self performSelectorInBackground:@selector(doSomething) withObject:nil];
如何检测到此操作的结束?
【问题讨论】:
标签: iphone multithreading ios detect nsthread
在 doSomething 方法的末尾调用?!
- (void)doSomething {
// Thread starts here
// Do something
// Thread ends here
[self performSelectorOnMainThread:@selector(doSomethingDone) withObject:nil waitUntilDone:NO];
}
【讨论】:
如果您只想知道它何时完成(并且不想传回太多数据 - 我会推荐一个代表),您可以简单地向通知中心发布通知。
[[NSNotificationCenter defaultCenter] postNotificationName:kYourFinishedNotificationName object:nil];
在您的视图控制器 viewDidLoad 方法中添加:
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(yourNotificationListenerMethod:)
name:kYourFinishedNotificationName
object:nil];
在dealloc中,添加:
[[NSNotificationCenter defaultCenter] removeObserver:self];
【讨论】:
您可能希望在 doSomething 选择器完成后将其返回。 performSelectorInBackground 上发生的事情是 API 内部的,如果您想要更多控制权,您可能需要使用 performSelector:onThread:withObject:waitUntilDone: 并定期检查传递的线程上的 isFinished。我相信你更关心 doSomething 完成而不是实际线程,所以只需从那里发回。
【讨论】:
我创建了一个通用的后台处理程序来解决这个问题。只有第一种方法是公开的,所以它可以在整个过程中使用。请注意,所有参数都是必需的。
+(void) Run: (SEL)sel inBackground: (id)target withState: (id)state withCompletion: (void(^)(id state))completionHandler // public
{
[(id)self performSelectorInBackground: @selector(RunSelector:) withObject: @[target, NSStringFromSelector(sel), state, completionHandler]];
}
+(void) RunSelector: (NSArray*)args
{
id target = [args objectAtIndex: 0];
SEL sel = NSSelectorFromString([args objectAtIndex: 1]);
id state = [args objectAtIndex: 2];
void (^completionHandler)(id state) = [args objectAtIndex: 3];
[target performSelector: sel withObject: state];
[(id)self performSelectorOnMainThread: @selector(RunCompletion:) withObject: @[completionHandler, state] waitUntilDone: true];
}
+(void) RunCompletion: (NSArray*)args
{
void (^completionHandler)(id state) = [args objectAtIndex: 0];
id state = [args objectAtIndex: 1];
completionHandler(state);
}
这是一个如何调用的示例:
NSMutableDictionary* dic = [[NSMutableDictionary alloc] init];
__block BOOL done = false;
[Utility Run: @selector(RunSomething:) inBackground: self withState: dic withCompletion:^(id state) {
done = true;
}];
【讨论】: