转自IOS软件开发揭密:iPhone&iPad企业应用和游戏开发
IOS提供了一种“同步的”消息通知机制,观察者只要向消息中心注册,即可接收其他对象发送来的消息,消息发送者对消息接收者的情况可以一无所知,两者完全解耦。
这种消息通知机制可以应用于任意事件和任何对象,观察者可以有多个,所以消息具有广播的性质,只是需要注意的是,观察者向消息中心注册以后,在不需要接收消息时需要向消息中心注销,这种消息广播机制是典型的Observer模式,应用这种模式需要5个步骤:
步骤1:
定义消息。这里定义一个全局的字符串常量NOTIF_DataComplete,代码如下,
//notifsAppDelegate.h
//For name of notification
extern NSString * const NOTIF_DataComplete;
@interface notifsAppDelegate : NSObject <UIApplicationDelegate>
{
UIWindow *window;
}
@property (nonatomic, retain)IBOulet UIWindow *window;
@end
步骤2:发送消息,调用postNotificationName()发送消息给观察者,代码如下,
//notifsAppDelegate.m
#import *notifsAppDelegate.h
#import "SomeClass.h"
//For name of notification
NSString *const NOTIF_DataComplete = @"DataComplete";
@implementation notifsAppDelegate
-(void)applicationDidFinishLaunching : (UIApplication *)application
{
[window makeKeyAndVisible];
SomeClass *someclass = [[SomeClass alloc] init];
//post a notification that the data has been downloaded
[[NSNotificationCenter defaultCenter] postNotificationName : NOTIF_DataComplete object:nil];
}
步骤3:观察者注册消息,代码如下:
//SomeClass.m
-(void )init
{
//Register observer for when download of data is complete
[[NSNotificationCenter defaultCenter] addObserver: self selector:@selector(downloadDataComplete:) name:NOTIF_DataComplete object:nil];
}
步骤4:观察者处理消息。实现downloadDataComplete()函数,代码如下:
//SomeClass.m
-(void) downloadDataComplete:(NSNotification *)notif
{
NSLog(@"Received Notification - Data has been downloaded");
}
步骤5:观察者注销,代码如下:
//SomeClass.m
-(void)dealloc
{
[[NSNotificationCenter defaultCenter] removeObserver:self];
[super dealloc];
}
"Observer"模式的接口编程分为两部分,即步骤1和步骤2的消息接口定义以及后面3步的接口消息。
使用NSNotificationCenter 时如果有参数要传递时可以通过
[[NSNotificationCenter defaultCenter] postNotificationName : NOTIF_DataComplete object:nil]; object后面带参数进行传递。
如果传递的参数有多个可以通过
[[NSNotificationCenter defaultCenter] postNotificationName : NOTIF_DataComplete object:nil userInfo: nil]; userInfo后面跟的是一个NSDictionary,我们可以将要传递的多个参数都装到NSDictionary然后进行传递。取出来的时候只要通过notification.userInfo来取得这个字典。
重要提示:应用这种模式需要注意的是消息中心对消息的分发是同步的,也就是说消息在发送到下一个接收者之前需要前一个接受者快速返回,否则就会阻塞下一个接收者消息,所以对于长时间的消息处理,需要另外启动一个线程来单独处理消息接收后的任务,确保在接收到消息以后立即返回。