- 在 Swift 中,枚举类型是一等(first-class)类型
- 枚举是一种数据类型, 为一组相关的值定义了一个共同的类型
- Swift 中的 enum 与 Objective-C 的 enum 不同, Swift 的枚举成员在被创建时不会被赋予一个默认的整型值
- Objective-C enum 的成员值只能为整型, 但 Swift 中的 enum 不仅可以是整型,还能是字符型或浮点型
- Swift 中的 enum 除了成员值外,还有关联值(高级用法)
在学习 enum 的高级使用之前,首先需要了解 enum 的基本使用:
枚举的基本定义
enum Direction {
case north
case south
case east
case west
}
// 简写
enum Direction1 {
case north, south, east, west
}
// 用法:
// enum 常量
let direction = Direction.south
// enum 变量
var direction1 = Dreection.east
direction1 = .west
带有成员值的枚举
- 原始值, 如果定义了一个原始值,且为 Int,默认递增
- 如果在定义枚举类型的时候使用了原始值,那么将会自动获得一个初始化方法,这个方法接收一个叫做rawValue的参数,参数类型即为原始值类型,返回值则是枚举成员或nil
- 关联值是创建一个基于枚举成员的常量或变量时才设置的值,枚举成员的关联值可以变化
// 定义了原始值(成员值)后,且为 Int,默认递增
enum Direction2: Int {
case north = 0
case south
case east
case west
}
// 定义原始值为字符串类型
enum Drection3: String {
case north = "NORTH"
case south = "SOUTH"
case east = "EAST"
case west = "WEST"
}
// 如果定义了原始值,可以通过 rowValue 获取存储的值
let direction2WestNumber = Direction2.west.rawValue // 2
let direction3EastString = Direction3.east.rawValue // "EAST"
使用 Switch 语句匹配枚举值
var direction = Direction.south
switch direction {
case .north:
print("N")
case .south:
print("S")
case .east:
print("E")
case .west:
print("W")
}
// 打印: "S"
注意:
当通过 switch 匹配枚举值时,如果每个属性都匹配到,不需要调用 default
当只匹配了部分属性时,必须要调用default
direction = .east
switch direction {
case .north:
print("N")
case .south:
print("S")
default:
print("other direction")
}
// 打印: "other direction"
枚举与关联值
- Swift 的枚举中可以把其他类型的关联值和成员值一起存储起来使用
- 如果需要的话,每个枚举成员的关联值类型可以各不相同
具体使用
enum ValueEnum {
case num(Int)
case score(Float)
case string(String)
case dict([String: AnyObject])
}
var value = ValueEnum.num(5)
switch value {
case .num(let n):
print("IntValue: \(n)")
case .score(let f):
print("FloatValue: \(f)")
case .string(let s):
print("StringValue: \(s)")
case .dict(let d):
print("DictValue: \(d)")
}
// 打印: IntValue: 5
// 当修改 枚举成员 value 的值后, switch 打印的结果:
value = ValueEnum.score(8.8)
// 打印: FloatValue: 8.8
value = ValueEnum.string("Hi Mazy")
// 打印: StringValue: Hi Mazy
value = ValueEnum.dict(["key":"value" as AnyObject])
// 打印: DictValue: ["key": value]
枚举关联值的实际使用示例
通过枚举返回网络请求的返回结果
1-定义枚举类型,关联请求结果,包含成功的 json 数据,以及失败错误信息 error 数据
enum ResponseResult {
case json([String: AnyObject])
case error(Error)
}
2-定义网络请求函数,通过闭包返回结果信息,结果信息类型为枚举
func getData(with url: String, completionHandler: @escaping (ResponseResult)->Void) {
Alamofire.request(url).responseJSON { (response) in
if let json = response.result.value as? [String: AnyObject] {
completionHandler(.json(json)) // 请求成功,关联 json 数据
} else {
if let error = response.error {
completionHandler(.error(error)) // 请求失败,关联 error 数据
}
}
}
}
3-调用网络请求方法,通过 switch 处理返回结果数据
getData(with: "https://httpbin.org/get") { (result) in
switch result {
case .json(let json): // 如果请求成功,获取枚举关联的 json 数据
print(json)
case .error(let error):
print(error) // 如果失败,获取枚举关联的 error 数据
}
}