函数模块的补充
@inline(never) func xxxx 永远不内联 @inline(__always) func xxxx 永远内联,除非是递归等无法内联的(前提是开启了编译器优化)
inout(本质并不是引用传递,后面会有详述)
枚举
enum Direction
{
case north
case west
case east
case south
}
如上所示,一般的枚举就是提供一个类似的可选项,swift也不例外,只是它的功能要更大强大一点,准确说是和switch用要更加牛掰
let n = direction.north
switch n
{
case direction.north:
print("north")
case direction.west:
print("west")
case .east:
print("east")
case .south:
print("south")
default:
break
}
比如可以像这么用,最终结果是输出north,一个注意点,这里.前面加不加direction没区别,它会自动去找对应的枚举
关联值
关联值可以算是一种可选的成员变量类型,比如说当成绩有两种形式的时候,1.分数2.等级那么代码就可以写成这样
成绩是个分数的时候则调用point,成绩是个评级就调用rank,然后在switch里面进行不同的操作即可
这个不贴切,再比如时间,是有两种形式的
上面可以用于各种计算,下面可以用于展示
原始值
原始值可以理解成是一种默认值
就是预先写好的值,如图所示,调用也是需要rawValue才能调用实际值,这是个内存的考虑,后面会记录
还有一种隐式原始值,比如拿方向举例
这两者的输出是一样的,因为给定了类型但是没赋值的话,就会生成默认值,Int一般就是0,1,2,3这样,String则会生成对应名称的字符串
递归枚举
先说说关键字 indirect,
如图就是一个简单的递归枚举的声明,但只是声明了并没有用
这是个递归枚举的实际使用例子,个人不是很建议这么写,程序还是应该简洁明了,这写的人都能绕晕了,目的就是完成10 + 5 - 2,最后输出的结果是13,了解下就好,也许会有业务需要这个
枚举内存结构
MermoryLayout直译就是内存布局,可以访问很多内存信息,比如占的分配的内存数,实际占用的内存,内存对齐等等,功能比教程中的要多的多
比如一个Int
这里的全是8,从上到下分别是分配的实际占用的内存大小,内存对齐的大小,内存大小单从Int是看不出区别的
用枚举会更明显一点
输出的结果是33 40 8,这里重点的就是1,字符串的内存大小是16,理论上内存对齐是16而不是8,原因就是枚举它默认不会创建一个结构体,除非是number这种元组形似的,默认元组的一个case就是1个字节,它的底层只是给它加了个下标,除非调用才能去获取真正的值,所以str的值是1,32 + 1就是33了,这就是实际占用33的原因,但内存是会自动对齐的(cpu读取是有规则的比如1 ,2 ,4 ,8这样,如果全按1读,那效率未免也太低了,所以一般会读取最大的值,所以在内存分配的时候为了保证读取效率和读取的完整度,会有内存对齐概念,并且用的单一模块占用内存的最大值,比如这里就是Int)
这里也全都是1,可见枚举在处理相同类型的时候它是不会分配更多内存的,因为不管是哪个,它都只会选中一个,那么直接给它生成一个下标,等到需要实际值的时候再返回不就好了,而不同类型不是生成下标,而是分配空间的原因是因为不好识别(有啥不好识别的,下标0返回元组,下标1返回字符串不就完了,对于MJ的解释我有点存疑,持续了解吧)