常用的不说了,说一下我目前遇到的tip
发送通知与响应通知都在一个线程
这一点与KVO类似。
NSNotification不能跨线程:即响应通知的action,默认是与postNotification在同一个线程的,若想在指定线程中执行响应通知的方法,可以使用带有block的addObserver方法,或者使用dispatch_async(xxx)。
如果需要跨线程,可以使用带有block的通知接口。
dispatch_group_async(manager.completionGroup ?: url_session_manager_completion_group(), manager.completionQueue ?: dispatch_get_main_queue(), ^{
if (self.completionHandler) {
self.completionHandler(task.response, responseObject, error);
}
dispatch_async(dispatch_get_main_queue(), ^{
[[NSNotificationCenter defaultCenter] postNotificationName:AFNetworkingTaskDidCompleteNotification object:task userInfo:userInfo];
});
});
为了保证在主线程发送通知。 这一点可以在一些网络请求数据到达时, 用于刷新界面。
dispatch_async(dispatch_get_main_queue(), ^{
[[NSNotificationCenter defaultCenter] postNotificationName:kNotificationFilterMaterialRequestFinished object:self userInfo:nil];
});
在指定线程接收通知
使用queue和block
使用mach port
上面说到,收发都在一个线程中,如果想要做到,在某个指定的线程接收通知,该如何做呢?苹果文档上提及了实现思路。
先简单介绍下mach port,它主要用来线程间通信。简单来说,就是接收线程中注册NSMachPort,在另外的线程中使用此port发送消息,则注册线程会收到相应消息,调用handleMachMessage来处理。
主要思路:
定义一个中间对象NotificationHandler,用来专门接收通知,包括一个队列,接收通知的线程,mach port,lock。
首先NotificationHandler会注册一个通知,对应的处理函数为processNotification,当在其他线程中post时,processNotification会被调用,进行如下处理。如果收到的通知跟指定的线程一样,则处理消息,反之,则添加到队列,同时通过port发送消息给指定线程。注意多线程中,对队列的处理,要加锁。
指定线程收到回调handleMachMessage,首先会将通知删除,然后调用processNotification进行处理,继续以上过程。
。