【iOS_Development】delegate的使用优化

前言

  相信做过iOS开发的人都使用过delegate(并不是设置模式中的proxy),这里就以一个实例,来分享一下开发中大量使用某个delegate方法的优化方案

位段

位段,C语言允许在一个结构体中以位为单位来指定其成员所占内存长度,这种以位为单位的成员称为“位段”或称“位域”( bit field) 。利用位段能够用较少的位数存储数据。
struct data {
    unsigned int fieldA : 8;
    unsigned int fieldB : 4;
    unsigned int fieldC : 2;
    unsigned int fieldD : 1;
}

  在结构体中,fieldA位段将占用8个二进制位,fieldB占用4个,fieldC占用2个,fieldD占用1个。于是,fieldA可以表示0至255之间的值,而fieldD可以表示0或1这两个值,我们可以像fieldD这样,把委托对象是否实现了协议中的相关方法这一信息缓存起来。如果创建结构体中只有大小为1的位段,那么就能把许多Boolean值塞入一小块数据里面了。以网络数据获取器为例,可以在该实例中嵌入一个含有位段的结构体作为其实例变量,而结构体中的每个位段则表示delegate对象是否实现了协议中的相关方法

delegate缓存

@interface NetworkFetcher () {
    struct {
        unsigned int didReceiveData : 1;
        unsigned int didFailWithError : 1;
        unsigned int didUpdateProgressTo : 1;
    }_delegateFlags;
}

@end

  上面的实例变量是个结构体,其中含有三个位段,每个位段都与delegate所遵从的协议中某个可选(@optional)方法相对应。这个结构体用来缓存委托对象是否能响应特定的选择子,实现缓存功能所用的代码可以写在delegate属性所对应的设置方法里

- (void)setDelegate:(id)delegate {
    _delegate = delegate;

    _delegate.didReceiveData = [delegate respondsToSelector:@selector(NetworkFetcher:didReceiveData)];
    _delegate.didFailWithError = [delegate respondsToSelector:@selector(NetworkFetcher:didFailWithError)];
    _delegate.didUpdateProgressTo = [delegate respondsToSelector:@selector(NetworkFetcher:didUpdateProgressTo)];    
}

  这样的话,每次调用delegate的相关方法之前,就不用检测委托对象是否能响应给定的选择子了,而是直接查询结构体里的标识

if (_delegate.didUpdateProgressTo) {
    [_delegate NetworkFetcher:self didUpdateProgressTo:currentProgess];
}

  在相关方法要调用多次时,值得进行这种优化,而是否需要优化,则应依照具体代码来定。这就需要分析代码性能,并找出瓶颈,若发现执行速度需要改进,则可使用该技巧。如果要频繁通过数据源协议从数据源中获取多份相互独立的数据,那么这项优化技术极有可能会提高程序效率

  • 声明:本文摘自《Effective Objective C 2.0:编写高质量iOS与OS X代码的52个有效方法》

【iOS_Development】delegate的使用优化_第1张图片

你可能感兴趣的:(delegate,ios,ios开发,位段,优化,iOS_Development)