go的数组和切片
Bingo's Blog 2020-04-01 golang
数组是 同一种类型元素的集合,数组从声明时就确定,使用时可以修改数组成员,但是数组大小不能变化
# 数组定义
- var 数组变量名 [元素数量] T
var a[3]int
数组可以通过下标访问,下标从0开始,最后一个下标是len-1, 访问越界会panic
# 数组初始化
- 方法1:可以使用初始化列表来设置数组元素的值
func demo(){
var testArray [3]int
var numArray = [3]int{1,2}
var cityArray = [3]string{'bj','sh','sz'}
}
- 方法2:以上方法需要确保初始值和数组长度一致,另外我们可以让编译器根据初始值的个数自行判断数组的长度
func main(){
var numArray = [...]int{1,2}
var cityArray = [...]string{"1","2","3"}
}
- 方法3:使用指定索引值的方式来初始化数组
func main(){
a := [...]int{1:1,3:5}
fmt.Println(a) //[0 1 0 5]
fmt.Println("type of a:%T\n",a)//type of a:[4]int
}
# 数组的遍历
func main(){
var a = [...]string{"1","2","3"}
//方法1:for循环
for i :=0 ; i < len(a); i++ {
fmt.Println(a[i])
}
//方法2:for range 循环
for index , value := range a{
fmt.Println(index, value)
}
}
# 多维数组
- 定义
func main(){
a := [3][2]string{
{"1","2"},
{"3","5"},
}
fmt.Println(a)
fmt.Println(a[1][1])
}
- 遍历
func main(){
a := [2][2]string{
{"1","2"},
{"3","4"},
{"5","6"}
}
for _,v1 := range a{
for _,v2 := range v1{
fmt.Println("%s\t",v2)
}
}
}
注意:多维数组***只有第一层*** 可以使用...来让编译器推导数组长度
//支持的写法
a := [...][2]string{
{"北京", "上海"},
{"广州", "深圳"},
{"成都", "重庆"},
}
//不支持多维数组的内层使用...
b := [3][...]string{
{"北京", "上海"},
{"广州", "深圳"},
{"成都", "重庆"},
}
- 数组是值类型,赋值和传参会复制整个数组。因此改变副本的值,不会改变本身的值。
# 切片引入
# 数组的缺点
类型固定,不能动态改变新增元素
# 切片
切片是一个拥有相同类型元素的可变长度的序列,他是基于数组类型做的一层封装,它非常灵活,支持自动扩容 切片是一个引用类型,他的内部结构包括 地址 长度 和容量 切片一般用于快速地操作一块数据集合
# 声明
var name []T
- 其中 name是变量名,T表示切片类型
func main(){
var a []string
var b = []int{}
var c =[]bool{false,true}
var d = []bool {false,true}
fmt.Println(a)
fmt.Println(b)
fmt.Println(c)
fmt.Println(a == nil)
fmt.Println(c == d)
}
# 切片的长度和容量
切片拥有自己的长度和容量,可以使用内置的len()函数求长度,使用内置的cap()函数求切片容量
# 切片表达式
切片表达式中的low和high表示一个索引范围(左包含,又不包含),也就是下面代码中从数组a中选出1<=索引值<4的元素组成切片s,得到的切片长度=high-low,容量等于得到的切片的底层数组的容量。
func main() {
a := [5]int{1, 2, 3, 4, 5}
s := a[1:3] // s := a[low:high]
fmt.Printf("s:%v len(s):%v cap(s):%v\n", s, len(s), cap(s))
}
可以省略切片表达式中的任何索引,省略了low则默认为0,省略了high则默认为切片操作数的长度
a[2:] //等同于 a[2:len(a)]
a[:3] //等同于a[0:3]
a[:]//等同于a[0:len(a)]
# 注意
对于数组或者字符串,如果0<=low<=high<=len(a),则索引合法,否则就会索引越界 对切片再执行切片表达式时(切片再切片)high的上限边界是切片的容量cap(a), 而不是长度,常量索引必须是非负的,并且可以用int类型的值表示,对于数组或常量字符串,常量索引也必须在有效范围内,如果low和high两个指标都是常数,他们必须满足low <= high 如果索引在运行时超出范围,就会发生运行时panic