美文网首页
iOS 监听事件的方法

iOS 监听事件的方法

作者: 胖红Red | 来源:发表于2017-08-14 15:38 被阅读35次
    1. 通知(NSNotificationCenter\NSNotification)

    任何对象之间都可以传递消息

    使用范围

    1个对象可以发通知给N个对象

    1个对象可以接受N个对象发出的通知

    必须得保证通知的名字在发出和监听时是一致的

    2. KVO
    • 仅仅是能监听对象属性的改变(灵活度不如通知和代理)
    3. 代理

    使用范围

    1个对象只能设置一个代理(假设这个对象只有1个代理属性)

    1个对象能成为多个对象的代理

    比通知规范

    建议使用优先级代理->通知

    • 通知中心
    //接收通知
    [[NSNotificationCenter defaultCenter] addObserver:baby selector:@selector(eat:) name:@"通知的名称" object:baby2];
    //发布通知
    [[NSNotificationCenter defaultCenter] postNotificationName:@"通知的名称" object:baby2 userInfo:@{@"通知的key":@"通知的value"}];
    

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

     - (void)dealloc {
    
    [super dealloc];  非ARC中需要调用此句
    
    [[NSNotificationCenter defaultCenter] removeObserver:self];
    
    }
    
    • 代理
    1.定义一份协议

    协议名字的格式一般是:类名 + Delegate

    e.g UITableviewDelegate

    2.代理方法细节

    一般都是optional.

    一般以类名开头

    e.g. - (void)scrollViewDidScroll:

    一般都需要将对象本身传出去。

    比如:tableView的方法都会把tableView本身传出去

    3. 必选要遵守NSObject 协议

    比如@protocol btnDelegate <NSObject>

    #######4.声明一个代理属性

    代理的类型格式:id<协议> delegate

     @property (nonatomic, weak) id<btnDelegate> delegate;
    
    5.设置代理属性
     xxx.delegate = yyy;
    
    6.代理对象遵守协议,实现协议里面的方法。

    如果代理方法是@optional,那么需要判断方法是否有实现
    if ([self.delegate respondsToSelector:@selector(btn:didClicked:)]) {

    [self.delegate wineCell:self didClicked:btn.tag];
    

    }

    • 代理使用weak 属性

      weak指针主要用于“父-子”关系,父亲拥有一个儿子的strong指针,因此是儿子的所  有者;但是为了阻止所有权回环,儿子需要使用weak指针指向父亲;
      你的viewcontroller通过strong指针拥有一个UITableview,tableview的datasource和delegate都是weak指针,指向viewcontroller,防止回环
      

    weak:指明该对象并不负责保持delegate这个对象,delegate这个对象的销毁由外部控制,在dealloc 方法中会被销毁。

    strong:该对象强引用delegate,外界不能销毁delegate对象,会导致循环引用(Retain Cycles) 这也是我们经常说的内存泄露,该释放的内存并未释放!

    • 通知和代理的选择
    共同点

    利用通知和代理都能完成对象之间的通信

    (比如A对象告诉D对象发生了什么事情, A对象传递数据给D对象)

    不同点

    代理 : 一对一关系(1个对象只能告诉另1个对象发生了什么事情)

    通知 :多对多关系(1个对象能告诉N个对象发生了什么事情, 1个对象能得知N个对象发生了什么事情)

    通知 KVO Delegate

    1.效率上来讲:delegate 比nsnotification 高

    2.delegate 比notification 更加直接,最典型的特征是delegate方法往往需要关注返回值。

    而notification 最大的特色就是不关心接受者的态度, 我只管把通告放出来,你接受不接受就是你的事情,同时我也不关心结果

    3.和delegate一样,KVO和NSNotification的作用也是类与类之间的通信,与delegate不同的是:1)这两个都是负责发出通知,剩下的事情就不管了,所以没有返回值;2)delegate只是一对一,而这两个可以一对多。

    4.kvo 的使用:

    被观察者发出 addObserver:forKeyPath:options:context: 方法来添加观察者。
    然后只要被观察者的keyPath值变化(注意:单纯改变其值不会调用此方法,只有通过    getters和setters来改变值才会触发KVO),就会在观察者里调用方法observeValueForKeyPath:ofObject:change:context:
    观察者需要实现方法 observeValueForKeyPath:ofObject:change:context: 来对KVO发出的通知做出响应。
    
    这些代码都只需在观察者里进行实现,被观察者不用添加任何代码,所以谁要监听谁注册,然后对响应进行处理即可,使得观察者与被观察者完全解耦,运用很灵活很 简便;但是KVO只能检测类中的属性,并且属性名都是通过NSString来查找,编译器不会帮你检错和补全,纯手敲所以比较容易出错。
    

    5.nsnotification的使用

    这里的通知不是由被观察者发出,而是由NSNotificationCenter来统一发出,而不同通知通过唯一的通知标识名notificationName来区分,标识名由发送通知的类来起。
    
    首先被观察者自己在必要的方法A里,通过方法postNotificationName:object:来发出通知notificationName这样发送通知者这边的工作就完成了,每次A被调用,就会发送一次通知notificationName。
    
    然后谁要监听A的变化,就通过[NSNotificationCenter defaultCenter]的方法addObserver:selector:name:object:为观察者注册监听name为notificationName的通知然后每次发出name为notificationName的通知时,注册监听后的观察者就会调用其自己定义的方法notificationSelector来进行响应。
    
    NSNotification的特点呢,就是需要被观察者先主动发出通知,然后观察者注册监听后再来进行响应,比KVO多了发送通知的一步,但是其优点是监听不局限于属性的变化,还可以对多种多样的状态变化进行监听,监听范围广,使用也更灵活
    

    相关文章

      网友评论

          本文标题:iOS 监听事件的方法

          本文链接:https://www.haomeiwen.com/subject/leuurxtx.html