前言
Go语言的切片相当于动态数组,切片存放在内存的堆区
声明切片
- 没有指定切片长度时,切片容量和切片长度默认都为0,其中没有数据
声明时指定切片长度
- 指定了切片长度时,切片长度为指定值,切片的容量为大于等于指定值的最小偶数,其中数据都为默认值
1
| 切片名 := make([]数据类型, 切片长度)
|
定义切片
1
| var 切片名 []数据类型 = []数据类型{数据, 数据, ...}
|
获取切片元素的值
修改切片元素的值
获取切片长度
获取切片容量
- 容量大于等于长度
- 自动扩容时
- 如果没有超过1024字节,每次扩展为上次容量的2倍
- 如果超过了1024字节,每次扩展为上次容量的1.25倍
追加切片数据
- 在切片末尾追加数据,长度将自动扩容
- 如果扩容后切片长度小于等于4,那么切片的容量为切片的长度
- 如果扩容后切片长度大于4,那么切片的容量为大于等于切片的长度的最小偶数
因为当声明切片时指定了长度,并且将赋值默认值,所以这里的切片末尾指的指切片最大长度
1 2
| 切片名 = append(切片名, 数据) 切片名 = append(切片名, 数据, 数据, ...)
|
遍历切片
1 2 3 4
| for i := 0; i < len(切片); i++ { fmt.Println("切片下标: ", i) fmt.Println("切片元素: ", 数组名[i]) }
|
1 2 3 4
| for i, v := range 数组名 { fmt.Println("切片下标: ", i) fmt.Println("切片元素: ", v) }
|
切片的截取
指定区间
1
| 新的切片名 = 旧的切片名[开始位置下标:结束位置下标]
|
截取到末尾
从头开始截取
指定截取后的切片容量
- 新的切片的容量应当大于等于截取后的长度
- 新的切片的容量应当小于旧的切片的容量
1
| 新的切片名 = 旧的切片名[开始位置下标:结束位置下标:新的切片的容量]
|
改变数据
- 截取后的切片仍然属于旧的切片的一部分,所以当修改新的切片的数据时,旧的切片中数据也会发生改变
1 2
| 新的切片名[下标] = 新数据 fmt.Println(旧的切片名[下标])
|
切片数据的拷贝
- 将旧切片中的数据拷贝到新切片中
- 切片数据拷贝时,要求新的切片的容量大于等于旧的切片的长度
- 拷贝操作得到的新切片与旧切片是两个单独的切片,数据不会相互影响
1 2 3
| var 旧的切片名 []数据类型 = []数据类型{} 新的切片名 = make([]数据类型, len(旧的切片名)) copy(新的切片, 旧的切片)
|
只拷贝部分数据
- 切片数据拷贝时,要求新的切片的容量大于等于产生的新的切片的长度
1
| copy(新的切片, 旧的切片[开始位置:结束位置])
|
切片作为函数参数
- 切片作为函数参数传递时是地址传递,形参可以改变实参的值
- 如果是修改切片内数据的操作,实参内的数据会跟随形参发生改变
- 如果是追加切片数据的操作,实参内的数据有可能不发生改变,因为在追加操作时,内存地址可能发生改变,不变实参指向的内存地址不变,所以实参内的数据可能不会发生改变
1 2 3 4 5
| func 函数名(切片名 []数据类型) {}
func main() { 函数名(切片名) }
|
切片作为返回值
1 2 3 4 5 6 7
| func 函数名(切片名 []数据类型) []数据类型{ return 切片名 }
func main() { 切片名 := 函数名(切片名) }
|
完成
参考文献
哔哩哔哩——喔咔咔耶耶