您的位置:首页 > 移动开发 > IOS开发

【iOS开发】观察者模式-通知的使用及深入理解

2015-03-29 01:25 543 查看
一、通知中心



1、概念:发生事件以后,以广播的形式通知所有监听者
2、通知中心的本质:
     (1)-通知中心的本质到底是什么?就是监听一个字符串!

  (2)- defaultCenter返回进程的默认通知中心!开发的时候,不能创建通知中心!
 
  (3)-
通知中心一旦获取到"字符串",就以广播的形式广播字符串,可以有多个观察者!
3、通知中心常用方法:
(1)发布通知:

     - (void)postNotificationName:(NSString*)aName
object:(id)anObject userInfo:(NSDictionary*)aUserInfo;

          发布一个名称为aName的通知,anObject为这个通知的发布者,aUserInfo为额外信息

(2)注册通知:

     - (void)addObserver:(id)observer
selector:(SEL)aSelector name:(NSString*)aName
object:(id)anObject;

    Øobserver:监听器,即谁要接收这个通知

    ØaSelector:收到通知后,回调监听器的这个方法,并且把通知对象当做参数传入

    ØaName:通知的名称。如果为nil,那么无论通知的名称是什么,监听器都能收到这个通知

    ØanObject:通知发布者。如果为anObject和aName都为nil,监听器都收到所有的通知

 (3)移除通知:

          一般在监听器销毁之前取消注册(如在监听器中加入下列代码):
     - (void)dealloc {

  //[super dealloc]; 非ARC中需要调用此句

    [[NSNotificationCenterdefaultCenter]removeObserver:self];
     }

4、常见系统通知:
 UIDevice对象所发布通知的名称常量

  ØUIDeviceOrientationDidChangeNotification//设备旋转

  ØUIDeviceBatteryStateDidChangeNotification//电池状态改变

  ØUIDeviceBatteryLevelDidChangeNotification//电池电量改变

  ØUIDeviceProximityStateDidChangeNotification//近距离传感器(比如设备贴近了使用者的脸部)

    
      键盘状态改变的时候,系统会发出一些特定的通知

  ØUIKeyboardWillShowNotification
// 键盘即将显示

  ØUIKeyboardDidShowNotification
//键盘显示完毕

  ØUIKeyboardWillHideNotification
// 键盘即将隐藏

  ØUIKeyboardDidHideNotification
// 键盘隐藏完毕

  ØUIKeyboardWillChangeFrameNotification
// 键盘的位置尺寸即将发生改变

  ØUIKeyboardDidChangeFrameNotification
//键盘的位置尺寸改变完毕

二、常见问题:
1、通知中心是同步的,还是异步的?-同步的!
【原因】



2 、通知里面到底有什么?
     - name          通知的名称字符串,通知中心本质上就是监听这个字符串
    - object        发布通知的时候,希望传递给监听者的对象
     - userInfo     发布通知的时候,希望传递给监听者的附加信息字典
 
3、 -通知和代理有什么区别?
    (1)-
代理是一对一的,设置 delegate 属性,在需要的时候,通过 delegate调用 selector方法!
    (2)-
通知是一对多的,只要发生事件,会以广播的形式,通知所有的监听者
    (3)- 通知中心/发布通知的对象不需要知道谁是监听者,发布对象和监听者之间的耦合度很低

    (4)- 监听者需要知道通知的名称字符串,如果发布者还传递 userInfo 字典,监听者同时需要知道字典的键名
    (5)-技巧:遵循苹果设计,在OC的框架中,如果定义通知,通常通知的名字包含"Notification"字样,同时key会和通知定义在一起!



(6)- 通知监听方法不能有返回值!
(7)-
代理可以有返回值!

三、设计原则
 对于一些对性能消耗比较大的功能:

 例如:地图导航(GPS),利用加速计/陀螺仪,通知中心……

 可以在界面出现的时候,开启功能,界面消失的时候,关闭功能,能够达到省电的目的!

 如果是通知中心,利用这一技巧,可以避免和其他的界面中监听相同事件发生冲突!
// 将要出现
- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
// 监听文本变化
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(textChanged:) name:UITextFieldTextDidChangeNotification object:nil];
}

// 将要消失
- (void)viewWillDisappear:(BOOL)animated {
[super viewWillDisappear:animated];
//移除通知
[[NSNotificationCenter defaultCenter] removeObserver:self];
}

四、通知队列
1、本质:通知队列就是一个缓存,用来存放通知,判断在适当的时候发布
2、【注意】
    通知队列是一个缓冲,可以判断什么时候来发布通知!

     利用发送通知的 Style,同样可以实现简单的异步!
    提示:通知中心本身的工作机制没有发生任何变化,变化的是队列的缓冲效果!

3、两个入队方法
【例子】先创建一个通知对象和队列
// 通知队列
NSNotificationQueue *q = [NSNotificationQueue defaultQueue];

// 入队
NSNotification *n = [NSNotification notificationWithName:@"QueueDemoNotification" object:@"hello"];

(1)   /**

NSPostWhenIdle = 1,    Idle 发呆,空闲时发布
NSPostASAP = 2,        ASAP as soon as possible尽快
NSPostNow = 3          立即发布
*/
[q enqueueNotification:n postingStyle:NSPostASAP];

(2)
/**
NSPostWhenIdle = 1,    Idle 发呆,空闲时发布
NSPostASAP = 2,        ASAP as soon as possible尽快
NSPostNow = 3          立即发布

coalesce : 合并/聚合
NSNotificationNoCoalescing = 0,        不合并
NSNotificationCoalescingOnName = 1,    按照名称合并
NSNotificationCoalescingOnSender = 2   按照发布者合并

合并的用处:有的时候,可能会接收到多个通知,但是程序只想做出一次响应!
发布者可以利用通知队列,指定监听者工作几次!
*/
// 最后一个参数,指定发布通知的运行循环的模式数组,使用 nil,就是 默认的运行循环模式
[q enqueueNotification:n postingStyle:NSPostWhenIdle coalesceMask:1 forModes:nil];
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: