zoukankan      html  css  js  c++  java
  • iOS7 CookBook精彩瞬间(二)NSSet、通过Subscript访问类成员等

    1.NSSet的用法

       ①NSSet是一种无序集合,基于hash实现,可以在线性时间复杂度内查找某个元素,如果要让元素有序,应当使用NSOrderedSet,要让集合可变,与NSArray类似,使用NSMutableSet和NSMutableOrderedSet即可。

       ②从Set中取出元素只能用anyObject随机取,NSSet被系统用于存放用户的触摸点。

       ③Set的另一个特点是集合内元素唯一,重复向集合内添加同一元素是无效的。如果要实现集合中有多个重复元素,应该使用NSCountedSet。

       ④NSCountedSet本身是可变的,其元素重复原理是对元素个数进行计数,而不是真正的重复,调用方法countForObject:可以得到某个元素的个数。


    2.在自定义的类内实现用下标访问成员变量

       我们知道字典可以通过key拿到数据,如果类实现了字典的两个方法,借助于KVC可以实现下标访问,下面用一个例子来说明。

       按照CookBook中的例子,一个Person类有firstName和lastName两个成员,我们借助于键值来访问,需要实现两个方法:

    - (id)objectForKeyedSubScript:(id<NSCopying>)paramKey;
    - (void)setObject:(id)paramObject forKeyedSubscript:(id<NSCopying>)paramKey;
       苹果官方也许并不推荐这种做法,因此默认是没有提示的,有个技巧是先让类继承NSDictionary,然后可以根据提示打出这两个方法,然后再替换为NSObject或者其他基类。

       这两个方法一定要写在头文件里,然后就可以像字典那样访问成员变量了,如果不写在头文件,编译器会报错。

       下面是完整的代码:

       1.头文件

    #import <Foundation/Foundation.h>
    
    extern NSString *const kFirstNameKey;
    extern NSString *const kLastNameKey;
    
    @interface Person : NSObject
    
    @property (nonatomic, copy) NSString *firstName;
    @property (nonatomic, copy) NSString *lastName;
    
    - (id)objectForKeyedSubScript:(id<NSCopying>)paramKey;
    - (void)setObject:(id)paramObject forKeyedSubscript:(id<NSCopying>)paramKey;
    
    @end
        2.m文件,注意对键值的安全处理

    #import "Person.h"
    
    NSString *const kFirstNameKey = @"firstName";
    NSString *const kLastNameKey = @"lastName";
    
    @implementation Person
    
    - (id)objectForKeyedSubScript:(id<NSCopying>)paramKey{
        
        NSObject<NSCopying> *keyAsObject = (NSObject<NSCopying> *)paramKey;
        if ([keyAsObject isKindOfClass:[NSString class]]) {
            NSString *keyStr = (NSString *)paramKey;
            if ([keyStr isEqualToString:kFirstNameKey] || [keyStr isEqualToString:kLastNameKey]) {
                return [self valueForKey:keyStr];
            }
        }
        
        return nil;
        
    }
    
    - (void)setObject:(id)paramObject forKeyedSubscript:(id<NSCopying>)paramKey{
        
        NSObject<NSCopying> *keyAsObject = (NSObject<NSCopying> *)paramKey;
        if ([keyAsObject isKindOfClass:[NSString class]]) {
            NSString *keyStr = (NSString *)paramKey;
            if ([keyStr isEqualToString:kFirstNameKey] || [keyStr isEqualToString:kLastNameKey]) {
                [self setValue:paramObject forKey:keyStr];
            }
        }
        
    }
    
    - (NSString *)description{
        
        return [NSString stringWithFormat:@"%@ %@",_firstName,_lastName];
        
    }
    
    @end
        接下来我们就可以直接通过key访问成员变量了,之所以重写了description方法,就是为了打印出成员,来验证key可以设定值。

        验证代码如下:

    Person *p = [Person new];
    p[kFirstNameKey] = @"Tim";
    p[kLastNameKey] = @"Cook";
    NSLog(@"%@",p);
        打印如下:

    2015-08-31 18:19:44.742 iOS CookBookLearn[2825:36849] Tim Cook
        可以验证我们实现了通过key来访问成员变量。


    3.alertView判断按钮的清晰写法

       因为alertView在代理方法被调用时传入的是alertView本身和buttonIndex,一个常用的判断是直接判断buttonIndex等于几,这样对于大项目来说会提高交流成本,使得程序的可读性下降,一个比较好的办法是通过alertView的buttonTitleAtIndex:方法拿到标题,然后通过标题判断。


    4.对于默认宽高的控件,设置frame时width和height直接写0即可。


    5.DatePicker的成员属性minimumDate和maximumDate可以设置日期拾取区间限制。


    6.在iOS7和以后,UISlider的track images的宽度被限制为1,因此使用track image来自定义UISlider意义不大,应该使用minimumTrackTintColor和maximumTrackTintColor来设置轨道颜色。Slider的thumb宽高均为23,这也决定了Slider的默认高度为23不能改变。


    7.通过XIB加载视图,使用initWithNibName:bundle:方法,默认的bundle直接填nil即可。


  • 相关阅读:
    猴子搬香蕉问题
    IE浏览器上传文件后返回结果会自动弹出下载框
    webstorm忽略node_modules目录
    webstorm中sass编译时目录或内容包含中文字符报错
    echarts实现自动轮播tooltip
    IIS处理并发请求时出现的问题及解决
    Zuul 2.1.5 设计分析
    基于 Canal 设计可扩展、高可用 binlog 同步集群
    k8s-coredns内部解析
    Istio使用Envoy转发Http请求错误码426 Upgrade Required
  • 原文地址:https://www.cnblogs.com/aiwz/p/6154034.html
Copyright © 2011-2022 走看看