通过切片,我们可以动态灵活存储管理学生姓名,年龄等信息,比如:
names := []string{"sbh", "sgg", "xhz"}
ages := []int{22, 23, 24}
fmt.Println(names)
fmt.Println(ages)
但是如果我想获取张三的年龄,这是一个再简单不过的需求了,但是却非常麻烦,我们需要先获取张三的切片索引,再去ages切片中对应的索引取出,前提还得是姓名、年龄按索引对应存储。
所以在主流的编程语言中都会存在一种映射(key-value)类型,在 JS 中叫 json 对象类型,在Python中叫字典(dict)类型,而在Go语言中则叫 Map 类型。
Map是一种通过key来获取value的一个数据结构,其底层存储方式为数组,在存储时key不能重复,当key重复时,value进行覆盖,我们通过key进行hash运算(可以简单理解为把key转换为一个整型数字)然后对数组的长度取余,得到key存储在数组的哪个下标位置,最后将key和value组装为一个结构体,放入数组下标处。
1、map的声明
不同于切片根据索引查找值,map类型是根据key查找值。
map是引用类型,声明语法:
var map_name map[key_type]value_type
其中:
- map_name 为map的变量名
- key_type 为键类型
value_type是键对应的值类型
var info map[string]string
fmt.Println(info) // map[]
2、map的初始化
先声明再赋值
//var info map[string]string //没有默认空间
info := make(map[string]string, 3) // 引用类型,需要开辟空间
info["name"] = "shb"
info["age"] = "22"
fmt.Println(info) //map[age:22 name:shb]
map的键值是无序的。
直接声明变量
var info = map[string]string{"name": "sbh", "age": "22"}
fmt.Println(info) // map[age:22 name:sbh]
3、访问map
通过key访问值 ```go var info = map[string]string{“name”: “sbh”, “age”: “22”}
val, isExist := info[“name”] // 判断某个键是否存在map数据中
if isExist { fmt.Println(val) fmt.Println(isExist) } else { fmt.Println(“键不存在!”) }
- 循环访问所有键值
```go
var info = map[string]string{"name": "sbh", "age": "22"}
for key, value := range info {
fmt.Println(key, value)
}
4、map容量
和数组不同,map 可以根据新增的 key-value 动态的伸缩,因此它不存在固定长度或者最大限制,但是也可以选择标明map的初始容量capacity,格式如下:
make(map[keyType]valueType,cap)
例如:
map2 := make(map[string]float, 100)
当map增长到容量上限的时候,如果再增加新的 key-value,map的大小会自动加 1,所以处于性能的考虑,对于大的map或者会快速扩张的map,即使只是大概知道容量,也最好标明。
5、删除元素
一个内置函数 delete(),用于删除容器内的元素。
map2 := map[string]string{"name": "shuaigg", "age": "22"}
delete(map2, "age")
fmt.Println(map2) // map[name:shuaigg]
如果想清空一个map,最优的方式创建一个新的map!
6、map的灵活运用
// 案例1
data := map[string][]string{"jiangsu": []string{"nanjing", "suzhou", "wuxi"}, "shanghai": []string{"Jidding"}}
fmt.Println(data["jiangsu"][1]) // suzhou
// 案例2
data := map[int]map[string]string{1001: {"name": "sgg", "age": "23"}, 1002: {"name": "sbh", "age": "33"}}
fmt.Println(data[1001]["age"]) // 23
// 案例3
data := []map[string]string{{"name": "sgg", "age": "23"}, {"name": "sgg", "age": "23"}}
fmt.Println(data[0]["name"]) // sgg