内存分析
思考枚举变量的内存布局
// 观察原始值
enum Test {
case test1,test2,test3
}
//枚举的取值范围是0x00 ~ 0xFF共256个
var t = Test.test1
// 通过小工具打印枚举变量的内存地址
print(Mems.ptr(ofVal: &t)) // 0x0000000100008730
t = .test2
t = .test3
print(MemoryLayout<Test>.size)
print(MemoryLayout<Test>.stride)
print(MemoryLayout<Test>.alignment)
image.png
image.png
image.png
image.png
所以从图上可以看出
test1 在内存中存储是0 test2是1 test3是2
即使如下这样写,依然是原始值,内存分布和上面是没有区别的
// 在swift中64位Int是占8个字节,32位Int是占4个字节
enum Test: Int {
case test1 = 1,test2 = 2,test3 = 3
}
var t = Test.test1
print(Mems.ptr(ofVal: &t))
t = .test2
t = .test3
image.png
关联值的内存分布
enum TestEnum {
case test1(Int, Int, Int)//24
case test2(Int, Int)//16
case test3(Int)//8
case test4(Bool)//1
case test5
}
//02 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 t1 = TestEnum.test1(2, 3, 4)
print(Mems.ptr(ofVal: &t1))
//08 00 00 00 00 00 00 00
//09 00 00 00 00 00 00 00
//00 00 00 00 00 00 00 00
//01
//00 00 00 00 00 00 00
t1 = TestEnum.test2(8, 9)
//06 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
t1 = TestEnum.test3(6)
//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
t1 = TestEnum.test4(true) // Bool值在内存中占一个字节true为01 false为00
//00 00 00 00 00 00 00 00
//00 00 00 00 00 00 00 00
//00 00 00 00 00 00 00 00
//04
//00 00 00 00 00 00 00
t1 = TestEnum.test5
print(MemoryLayout<TestEnum>.size)//25
print(MemoryLayout<TestEnum>.stride) //32
print(MemoryLayout<TestEnum>.alignment)// 8
image.png
image.png
总结:
1.一个字节存储成员 2.N个字节存储关联值(N取决于占用内存最大的关联值),任何一个case的关联值都共用这N个字节
,上述中24>16>8>1所以最大是243.原始值后面的值是不占用枚举变量内存的(至于rawVlaue存储在哪里,有可能都不会存储,通过方法来换取的,不知占用内存)
image.png
重点理解这句话的含义:
image.png
注意点:
当枚举只有一个成员时,成员是不用耗费一个字节来存储的,因为不用去区分成员事实打印出来也是这样,虽然开辟了但是没有用到.
enum TestEnum {
case test1(Int, Int, Int)//24
}
print(MemoryLayout<TestEnum>.size)//24
print(MemoryLayout<TestEnum>.stride)//24
print(MemoryLayout<TestEnum>.alignment)//8
enum Test {
case test1
}
print(MemoryLayout<Test>.size)//0
print(MemoryLayout<Test>.stride)//1
print(MemoryLayout<Test>.alignment)//1
网友评论