美文网首页
iOS原生观察者模式&重新设计观察者模式

iOS原生观察者模式&重新设计观察者模式

作者: Jeff_Kitty | 来源:发表于2017-09-14 18:33 被阅读38次

           原生KVO的实现依赖于强大的runtime运行时机制,实现原理大致为:当观察某对象A的属性时,会动态的创建这个类的子类,并为这个新的子类重写了Setter方法,在这个Setter方法里面负责通知观察者属性变化的情况。

           前段时间面试的时候,面试官问我,如果不用系统的KVO模式,自己来实现一种设计模式,当时可能由于紧张,一下子没反应过来,最后结果可想而知,现在想来,对比现在所在的外包公司的种种不公平待遇,总结下来一句话,肚子里没货还真不行。

          闲话不多扯,先来简单说一下如何自己实现NSNotificationCenter通知模式,然后,细聊如何通过协议实现KVO,不同于原生KVO的实现方案。

          通知中心实现方案,首先进行角色划分,一个单例类A+抽象协议接口(包含接收到通知后实现的接口和发出通知的接口)Protocol+具体的实现类B;

            客户端:    A   包含属性数组  ,B遵循Protocol,实现协议方法,A数组持有B对象,当A发出通知时,取出数组中的B对象,通过运行时,让B实现协议方法,从而达到通知的目的。

    这里,我们重点看一下KVO的实现方案,首先进行角色划分:

    第一步 : 抽象出接口:所有观察者必须遵循这个协议

    // 抽象观察者Observer

    @protocol Observer

    - (void)update:(Observable *)o msg:(NSObject *)msg;

    @end

    第二步:定义一个基类Observable,所有被观察者对象都必须继承于Observable基类

    // 注册观察者- (void)addObserver:(id)o;                                          
    // 删除观察者- (void)deleteObserver:(id)o;

    // 删除所有观察者
    - (void)deleteObservers;

    // 观察者数量
    - (NSInteger)countObserver;

    // 通知
    - (void)notifyObservers;

    - (void)notifyObservers:(NSObject *)msg;

    // 更新数据
    - (void)setChanged;

    // 取消更新
    - (void)clearChanged;

    // 获取更新状态
    - (BOOL)hasChanged;

    Observable.m文件实现:

    #import "Observable.h"@interface Observable()
    @property (nonatomic,strong) NSMutableArray *obsArray;
    @property (nonatomic,assign) BOOL changed;
    @end

    // 被观察者
    @implementation Observable
    - (instancetype)init{ 
           if (self = [super init]) {   
         _obsArray = [NSMutableArray array];       
     _changed = NO;    } 
      return self;}

    // 注册观察者
    - (void)addObserver:(id)o {    [_obsArray addObject:o];}
    // 删除观察者
    - (void)deleteObserver:(id)o {    [_obsArray removeObject:o];}
    // 删除所有观察者
    - (void)deleteObservers {    [_obsArray removeAllObjects];}
    // 观察者数量
    - (NSInteger)countObserver {    return _obsArray.count;}
    - (void)notifyObservers {    [self notifyObservers:nil];}
    - (void)notifyObservers:(NSObject *)msg
    {   
        if (!_changed) {        return ;    }   
        [self clearChanged];   
         for (idobj in _obsArray) {
    [obj update:self msg:msg];
    }
    }

    // 更新数据
    - (void)setChanged {
    _changed = YES;
    }

    // 取消更新
    - (void)clearChanged {
    _changed = NO;
    }

    // 获取更新状态
    - (BOOL)hasChanged {
    return _changed;
    }

    客户端实现:

    WXObservable *observable = [WXObservable new];

    [observable addObserver:[CoffeeObserver new]];

    [observable addObserver:[SimpleObserver new]];

    [observable setTitle:@"思维的切换"];

    [observable push];

    [observable push];

    [observable push];

    相关文章

      网友评论

          本文标题:iOS原生观察者模式&重新设计观察者模式

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