ios:关于枚举
在计算机科学理论中,枚举是一个被命名的整型常数的集合。定义形式如下:
enum 枚举名{ 标识符[=整型常数], 标识符[=整型常数], ... 标识符[=整型常数], } 枚举变量;
内存空间上,enum是枚举型 union是共用体,成员共用一个变量缓冲区。它不参加内存的占用和释放,枚举定义的变量可直接使用,甚至不用初始化。
如果枚举没有初始化,则从第一个标识符开始,顺次赋给标识符0, 1, 2, ...。下面示例枚举中 n1,n2,n3,n4分别为0,1,2,3
enum NSInteger{n1, n2, n3, n4}x;
但当枚举中的某个成员赋值后,其后的成员按依次 加1的规则确定其值。
enum NSInteger { n1, n2 = 0, n3 = 10, n4 }x;
上面枚举示例中,n1,n2,n3,m4 分别为0,0,10,11。
1. 枚举中每个成员(标识符)结束符是",", 不是";", 最后一个成员可省略 ","。
2. 初始化时可以赋负数,以后的标识符仍依次加1。
3. 枚举变量只能取枚举说明结构中的某个标识符常量,例如此时n4=11.
虽然枚举类型被定义为一个整型集合,但是我测试还是可以定义成字符串,声明如下:
但是用法与整型枚举有些区别,它不能像整型直接使用,直接输出永远是0,需要写一个方法进行转换你需要的字符串。
- (NSString*) colorConvertToString:(ThreeColor) aColor { NSString *result = nil; switch(aColor) { case blackColor: result = @"black"; break; case redColor: result = @"red"; break; case yellowColor: result = @"yellow"; break; default: result = @"unknown"; } return result; } 打印结果: NSLog(@"%@",[self colorConvertToString:redColor]); red
但一直觉得字符串枚举没有什么意义,从来没有用过。
枚举还支持位运算,比如在UIView类里面看到这样的定义。
typedef NS_OPTIONS(NSUInteger, UIViewAutoresizing) { UIViewAutoresizingNone = 0, UIViewAutoresizingFlexibleLeftMargin = 1 << 0, UIViewAutoresizingFlexibleWidth = 1 << 1, UIViewAutoresizingFlexibleRightMargin = 1 << 2, UIViewAutoresizingFlexibleTopMargin = 1 << 3, UIViewAutoresizingFlexibleHeight = 1 << 4, UIViewAutoresizingFlexibleBottomMargin = 1 << 5 };
1<<0,0表示不进行移位 1还是1;大于1的会进行移位所以十进制的值分别是
typedef NS_OPTIONS(NSUInteger, UIViewAutoresizing) { UIViewAutoresizingNone = 0, //十进制,指定的位数,二进制 UIViewAutoresizingFlexibleLeftMargin = 1 << 0, //1,0,01 UIViewAutoresizingFlexibleWidth = 1 << 1, //2,1,10 转换成 十进制 2 UIViewAutoresizingFlexibleRightMargin = 1 << 2, //4,2,100 转换成 十进制 4 UIViewAutoresizingFlexibleTopMargin = 1 << 3, //8,3,1000 转换成 十进制 8 UIViewAutoresizingFlexibleHeight = 1 << 4, //16,4,10000 转换成 十进制 16 UIViewAutoresizingFlexibleBottomMargin = 1 << 5 //32,5,100000 转换成 十进制 32 };
位运算的计算方式是将二进制转换成十进制,也就是说,枚举值里面存取的是 计算后的十进制值.但是注意字符串枚举不适用于位运算。
所以在代码中下面这样写是没有任何区别的。
[UIButton buttonWithType:UIButtonTypeCustom];
[UIButton buttonWithType:0];
枚举之间还可以这样写:(UIApplication.h)
typedef NS_OPTIONS(NSUInteger, UIInterfaceOrientationMask) { UIInterfaceOrientationMaskPortrait = (1 << UIInterfaceOrientationPortrait), UIInterfaceOrientationMaskLandscapeLeft = (1 << UIInterfaceOrientationLandscapeLeft), UIInterfaceOrientationMaskLandscapeRight = (1 << UIInterfaceOrientationLandscapeRight), UIInterfaceOrientationMaskPortraitUpsideDown = (1 << UIInterfaceOrientationPortraitUpsideDown), UIInterfaceOrientationMaskLandscape = (UIInterfaceOrientationMaskLandscapeLeft | UIInterfaceOrientationMaskLandscapeRight), UIInterfaceOrientationMaskAll = (UIInterfaceOrientationMaskPortrait | UIInterfaceOrientationMaskLandscapeLeft | UIInterfaceOrientationMaskLandscapeRight | UIInterfaceOrientationMaskPortraitUpsideDown), UIInterfaceOrientationMaskAllButUpsideDown = (UIInterfaceOrientationMaskPortrait | UIInterfaceOrientationMaskLandscapeLeft | UIInterfaceOrientationMaskLandscapeRight), };
有时候,常说枚举一个数组,这里枚举其实是遍历的意思。在ios中为我们提供了一个枚举的类。(NSEnumerator.h)
@protocol NSFastEnumeration - (NSUInteger)countByEnumeratingWithState:(NSFastEnumerationState *)state objects:(id __unsafe_unretained [])buffer count:(NSUInteger)len; @end @interface NSEnumerator : NSObject <NSFastEnumeration> - (id)nextObject; @end @interface NSEnumerator (NSExtendedEnumerator) @property (readonly, copy) NSArray *allObjects; @end
集合类(如:NSArray、NSSet、NSDictionary等)均可获取到NSEnumerator, 该类是一个抽象类,没有用来创建实例的公有接口。NSEnumerator的nextObject方法可以遍历每个集合元素,结束返回nil,通过与while结合使用可遍历集合中所有项。
示例:
NSArray *anArray = // ... ; NSEnumerator *enumerator = [anArray objectEnumerator]; id object; while ((object = [enumerator nextObject])) { // do something with object... }
遍历数组每个索引处的对象,你可以编写一个0到[array count]的循环,而NSEnumerator用来描述这种集合迭代运算的方式。
通过objectEnumerator向数组请求枚举器,如果想从后向前浏览集合,可使用reverseObjectEnumerator方法。在获得枚举器后,可以开始一个while循环,每次循环都向这个枚举器请求它的下一个对象:nextObject。nextObject返回nil值时,循环结束。
也可以自定义枚举器,要实现快速枚举就必须实现NSFastEnumeration协议,也就是
- (NSUInteger)countByEnumeratingWithState:(NSFastEnumerationState *)state objects:(id *)stackbuf count:(NSUInteger)len;
并且覆盖nextObject方法。
郑重声明:本站内容如果来自互联网及其他传播媒体,其版权均属原媒体及文章作者所有。转载目的在于传递更多信息及用于网络分享,并不代表本站赞同其观点和对其真实性负责,也不构成任何其他建议。