Golang Slice笔记


本笔记旨在记录Go语言中的底层内容学习过程,仅代表个人学习记录,阅读请注意鉴别版本及特性。
Slice 结构体
1 | type slice struct { |
array是一个unsafe的指针,指向的是底层存储元素的连续内存数组的起始位置。
len是切片的长度,即该slice所包含的元素数量,可通过len()
函数访问。
cap是当前切片的容量,即从array指针开始,底层数组可以容纳的元素总量,可通过cap()
函数访问。
一个切片变量本身只占用3个机器字节长度的大小,对切片进行切片操作,只会创建一个新的slice结构体,而不会拷贝底层数组的数据,该操作虽然效率很高,但也导致在这处会出现陷阱问题。
Slice创建
1 | func makeslice(et *_type, len, cap int) unsafe.Pointer { |
et *_type
: 描述切片元素类型的内部结构体,包含了元素大小、是否包含指针等信息。
len
, cap
: 用户指定的长度和容量。
执行时先检查创建安全性,如len < 0
,len > cap
,以及计算出的总内存大小et.Size_ * cap
是否溢出或超出最大内存分配限制maxAlloc,然后调用 mallocgc
在堆上分配一块连续的内存,最后返回新分配内存的起始地址 unsafe.Pointer
。
编译器会用这个指针、len
和 cap
来填充最终的 slice
结构体。
根据golang.org/issue/4085所述,为了更加清晰易懂,若出现make([]T, bignumber)
过大的情况,应使用“len out of range”来替代“cap out of range”