Objective-C枚举的使用,常见的方式总结,以便自己使用时方便查阅。
1. 枚举介绍
enum only
1
2
3
4
5
| enum
{
TMEnumTestOne,
TMEnumTestTwo,
};
|
- 这种枚举不推荐使用,因为不能用一种类型的方式表示枚举。
enum 类型
1
2
3
4
5
6
| typedef enum
{
TMEnumTestOne,
TMEnumTestTwo,
} TMEnumTest;
|
1
2
3
4
5
6
| enum TMEnumTest
{
TMEnumTestOne,
TMEnumTestTwo,
};
typedef enum TMEnumTest TMEnumTest;
|
- 这两种写法,将枚举描述为一个类型TMEnumTest。
但是这种写法也有局限性,在作为函数参数时,如果传入NSInteger类型的数据,则需要强制转换,否则会有类型不匹配的警告,所以这种方式也不推荐。如下图,
老式enum写法
1
2
3
4
5
6
| enum
{
TMEnumTestOne,
TMEnumTestTwo,
};
typedef NSUInteger TMEnumTest;
|
- 这种写法可以指定TMEnumTest的类型,并且作为函数参数时,传入的值不需要进行强制类型转换。
但是这种写法不会检查枚举的正确性,是好是坏需要自己判断,如下图。本人推荐这种写法。
新式enum写法
1
2
3
4
5
| typedef NS_ENUM(NSUInteger, TMEnumTest)
{
TMEnumTestOne,
TMEnumTestTwo,
};
|
1
2
3
4
5
| typedef NS_OPTIONS(NSUInteger, TMEnumTest)
{
TMEnumTestOne = 0,
TMEnumTestTwo = 1 << 0,
};
|
- NS_ENUM和NS_OPTIONS本质是一样的,仅仅从字面上来区分用途。NS_ENUM是通用情况,NS_OPTIONS一般用来定义位枚举。
参考链接
- 这种写法同样作为函数参数时,传入的值不需要进行强制类型转换。但是也同样不会检查枚举的正确性,和 老式enum写法 一样,如下图。
- 但是不同的是,新式enum写法 在使用switch时,会进行值的检测,如果枚举中无此值,则会弹出警告,如下图。这种方式见仁见智了。本人推荐这种写法。
2. 枚举最大值
对于一般的枚举,要获取枚举的最大值是很难的,因为随着枚举的扩充,最大值在不断变化,这时推荐使用一个固定的枚举表示最大值,例如:
1
2
3
4
5
6
7
| typedef NS_ENUM(NSUInteger, TMEnumTest)
{
TMEnumTestOne,
TMEnumTestTwo,
TMEnumTestMax, // 表示最大值
};
|
这样就可以使用TMEnumTestMax表示枚举TMEnumTest的最大值了。
3. 位枚举
位枚举是一种特殊的枚举,在apple的类中使用的很多,例如NSStringCompareOptions
等。
1
2
3
4
5
6
7
| typedef NS_OPTIONS(NSUInteger, TMEnumTest)
{
TMEnumTestOne = 0, // 0
TMEnumTestTwo = 1 << 0, // 1
TMEnumTestThree = 1 << 1, // 2
TMEnumTestFour = 1 << 2, // 4
};
|
- 位枚举的特点是可以使用位运算来处理枚举值,实际使用中可以用一个变量存储多个枚举值,表示互不影响的多个设置。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
| - (void) test
{
TMEnumTest test = TMEnumTestTwo|TMEnumTestThree; // 3
/* 添加TMEnumTestFour到test中(如test已经包含TMEnumTestFour,则test值不变)
当然这里也可以使用test += TMEnumTestFour,
但是注意 + 不能在test中已经包含TMEnumTestFour的情况下使用。
*/
test |= TMEnumTestFour; // 7
/* 将TMEnumTestThree从test中去除(如test不包含TMEnumTestThree,则test值不变)
当然这里也可以使用test -= TMEnumTestThree,
但是注意 - 不能在test中不包含TMEnumTestThree的情况下使用。
*/
test &= ~TMEnumTestThree; // 5
// 判断 TMEnumTestFour枚举 是否被包含
if ((test & TMEnumTestFour) == TMEnumTestFour)
{
NSLog(@"YES");
}
/* 判断 TMEnumTestFour枚举 是否被包含
因为 (test & TMEnumTestFour) 的结果不是 0,就是TMEnumTestFour本身,
而 TMEnumTestFour > 0 ,所以可以使用简易的判断
*/
if (test & TMEnumTestFour)
{
NSLog(@"YES");
}
}
|