枚舉

枚舉
關(guān)聯(lián)值
- 有時(shí)將枚舉的成員值跟其他類(lèi)型的關(guān)聯(lián)值存儲(chǔ)在一起,會(huì)非常有用

關(guān)聯(lián)值
caset let .points(i) let也可以定義為var
caset let .points(i) let 定義在 前面,表示 i 的類(lèi)型為let
case .digit(let year, let month, let day) let 定義在里面,分別表示不同的類(lèi)型,定義在外面的話(huà),里面只能是一種類(lèi)型
關(guān)聯(lián)值舉例
-
直接將值傳入到
舉例
原始值
- 枚舉成員可以使用相同類(lèi)型的默認(rèn)值預(yù)先對(duì)應(yīng),這個(gè)默認(rèn)值叫做原始值
- 原始值不占用枚舉變量的內(nèi)存

原始值
隱式原始值
- 如果枚舉的原始值類(lèi)型是Int,String,Swift會(huì)自動(dòng)分配原始值
- string的話(huà),名字是啥,值就是啥
- Int的話(huà),會(huì)自動(dòng)從0開(kāi)始累加(如指定,則從指定的值開(kāi)始累加)

隱式原始值
遞歸枚舉
- 里面的內(nèi)容使用了自己,如果是遞歸枚舉必須使用
indirect修飾 -
indirect可以放在枚舉的前面,也可以分別放

遞歸枚舉
MemoryLayout
- 可以使用MemoryLayout獲取數(shù)據(jù)類(lèi)型占用內(nèi)存的大小
-
stride分配的內(nèi)存大小size實(shí)際占用的大小alignment內(nèi)存對(duì)齊
enum Password {
case number(Int, Int, Int, Int) // 32
case other // 1
}
print("stride == \(MemoryLayout<Password>.stride)") // stride == 40
print("size == \(MemoryLayout<Password>.size)") // size == 33
print("alignment == \(MemoryLayout<Password>.alignment)") // alignment == 8
enum TestEnum {
case test1(Int, Int, Int)
case test2(Int, Int)
case test3(Int)
case test4(Bool)
case test5
}
/// 01 00 00 00 00 00 00 00
/// 03 00 00 00 00 00 00 00
/// 04 00 00 00 00 00 00 00
/// 00 00 00 00 00 00 00 00
var e = TestEnum.test1(1, 3, 4)
print(Mems.ptr(ofVal: &e))
/// 05 00 00 00 00 00 00 00
/// 00 00 00 00 00 00 00 00
/// 00 00 00 00 00 00 00 00
/// 02 00 00 00 00 00 00 00
e = .test3(5)
/// 01 00 00 00 00 00 00 00
/// 00 00 00 00 00 00 00 00
/// 00 00 00 00 00 00 00 00
/// 03 00 00 00 00 00 00 00
e = .test4(true)
觀(guān)察上面代碼,可以得出:
- 1個(gè)字節(jié)存儲(chǔ)成員變量 (0, 1, 2,3,4)存放的就是成員變量
- N個(gè)字節(jié)存儲(chǔ)關(guān)聯(lián)值(N取占用內(nèi)存最大的關(guān)聯(lián)值),任何一個(gè)case的關(guān)聯(lián)值都公用這N個(gè)字節(jié)
- 只有一個(gè)case時(shí),不會(huì)需要一個(gè)字節(jié)去存儲(chǔ)成員變量
enum Password {
case other(Int)
}
stride == 8
size == 8
alignment == 8
注意點(diǎn):觀(guān)察下面代碼
- 因?yàn)橹挥幸粋€(gè)值,不會(huì)先去占用內(nèi)存。
enum Password {
case other
}
print("stride == \(MemoryLayout<Password>.stride)") // stride == 1
print("size == \(MemoryLayout<Password>.size)") // size == 0
print("alignment == \(MemoryLayout<Password>.alignment)") // alignment == 1
