代码路径:Go slice和map
这一章要记住什么
这一章主要讲三个容器:
- 数组:长度固定,是值类型。
- 切片:长度可变,底层引用数组。
- map:键值对集合,用来按 key 查 value。
1. 数组
代码里:
var strArr = [10]string{"aa", "bb", "cc"}
arr := [3]int{1, 2, 3}
数组的长度是类型的一部分。
[10]string 和 [3]string 是两个不同类型。
strArr: [10]string
+----+----+----+----+-----+
| aa | bb | cc | "" | ... |
+----+----+----+----+-----+
0 1 2 3
没有显式初始化的位置,会使用元素类型的零值。
总结一下
数组适合长度固定的场景,但实际开发中切片用得更多。
2. 切片
代码里:
var sliceArr = make([]string, 0)
sliceArr = strArr[1:3]
[]string 是切片类型,和 [10]string 不一样。
strArr[1:3] 表示从下标 1 开始,到下标 3 之前结束。
所以拿到的是:
strArr:
index: 0 1 2 3
aa bb cc ""
strArr[1:3]
|
v
bb cc
切片本身可以理解成一个小结构:
slice
+---------+
| ptr | -> 指向底层数组某个位置
| len | -> 当前长度
| cap | -> 当前容量
+---------+
总结一下
切片不是数组本身,它更像是对底层数组的一段视图。
3. map
代码里:
var dic = map[string]int{
"apple": 1,
"banana": 2,
}
这是一个 key 是 string,value 是 int 的 map。
dic
+----------+-------+
| apple | 1 |
| banana | 2 |
+----------+-------+
总结一下
map 适合根据 key 快速找到 value,比如统计次数、保存配置、做索引。
4. fmt 输出
代码里用了:
fmt.Printf("%v\n", arr)
fmt.Printf("%+v\n", strArr)
对普通数组、切片、map 来说,%v 和 %+v 差别不明显。
%+v 在打印结构体时会额外带字段名,更常用于调试结构体。
总结一下
调试时先用 %+v 很方便,尤其是打印结构体和复杂对象。
易错点
- 数组长度是类型的一部分。
- 切片表达式左闭右开,比如
strArr[1:3]不包含下标3。 - 切片底层引用数组,修改切片元素可能影响原数组。
- map 没有固定顺序,遍历顺序不能依赖。
快问快答
Q1:数组和切片有什么区别?
答:
数组长度固定,长度是类型的一部分。切片长度可变,底层引用数组,实际开发更常用。
Q2:strArr[1:3] 包含哪些元素?
答:
包含下标 1 和 2,不包含下标 3。
Q3:map 适合什么场景?
答:
适合通过 key 快速查 value,比如计数、缓存、配置表、索引表。
一句话总结
数组管固定长度,切片管动态序列,map 管键值查找。

1146

被折叠的 条评论
为什么被折叠?



