通过切片,我们可以动态灵活存储管理学生姓名,年龄等信息,比如:

  1. names := []string{"sbh", "sgg", "xhz"}
  2. ages := []int{22, 23, 24}
  3. fmt.Println(names)
  4. 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是引用类型,声明语法:

  1. var map_name map[key_type]value_type

其中:

  • map_name 为map的变量名
  • key_type 为键类型
  • value_type是键对应的值类型

    1. var info map[string]string
    2. fmt.Println(info) // map[]

    2、map的初始化

  • 先声明再赋值

    1. //var info map[string]string //没有默认空间
    2. info := make(map[string]string, 3) // 引用类型,需要开辟空间
    3. info["name"] = "shb"
    4. info["age"] = "22"
    5. fmt.Println(info) //map[age:22 name:shb]

    map的键值是无序的。


  • 直接声明变量

    1. var info = map[string]string{"name": "sbh", "age": "22"}
    2. 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(“键不存在!”) }

  1. - 循环访问所有键值
  2. ```go
  3. var info = map[string]string{"name": "sbh", "age": "22"}
  4. for key, value := range info {
  5. fmt.Println(key, value)
  6. }

4、map容量

和数组不同,map 可以根据新增的 key-value 动态的伸缩,因此它不存在固定长度或者最大限制,但是也可以选择标明map的初始容量capacity,格式如下:

  1. make(map[keyType]valueType,cap)

例如:

  1. map2 := make(map[string]float, 100)

当map增长到容量上限的时候,如果再增加新的 key-value,map的大小会自动加 1,所以处于性能的考虑,对于大的map或者会快速扩张的map,即使只是大概知道容量,也最好标明。

5、删除元素

一个内置函数 delete(),用于删除容器内的元素。

  1. map2 := map[string]string{"name": "shuaigg", "age": "22"}
  2. delete(map2, "age")
  3. fmt.Println(map2) // map[name:shuaigg]

如果想清空一个map,最优的方式创建一个新的map!

6、map的灵活运用

  1. // 案例1
  2. data := map[string][]string{"jiangsu": []string{"nanjing", "suzhou", "wuxi"}, "shanghai": []string{"Jidding"}}
  3. fmt.Println(data["jiangsu"][1]) // suzhou
  4. // 案例2
  5. data := map[int]map[string]string{1001: {"name": "sgg", "age": "23"}, 1002: {"name": "sbh", "age": "33"}}
  6. fmt.Println(data[1001]["age"]) // 23
  7. // 案例3
  8. data := []map[string]string{{"name": "sgg", "age": "23"}, {"name": "sgg", "age": "23"}}
  9. fmt.Println(data[0]["name"]) // sgg