map类型
go语言利用hash表来实现,它是一个无序的key/value的集合,key唯一并且必须支持“==”运算符进行比较。
定义
var 变量名 map[key类型]value类型,由于map是一个引用类型,必须初始化才可以使用,对于切片来说,使用append函数会去分配内存空间,所以可以使用。
var map1 map[string]int
map1["nihao"] = 100
println(map1)
输出:
panic: assignment to entry in nil map [recovered]
map初始化
map1 := make(map[string]int)
map1 := make(map[string]int)
map1["nihao"] = 100
fmt.Println(map1)
输出:
map[nihao:100]
map1 := map[string]int{key:value,key:value}
其中“{}”内容可以为空,这时创建了一个内容空的map,并非nil。
map1 := map[string]int{
"nihao": 100,
"hello": 20,
}
fmt.Println(map1)
输出:
map[hello:20 nihao:100]
:=var
map元素不可取地址
map中的元素并不是一个变量,所以是不可以对map中的元素进行取地址操作。
map1 := map[string]int{}
map1["张三"] = 90
var a = &map1["张三"]//invalid operation: cannot take address of map1["张三"]
不能对map取地址的原因是map可能随元素的增加而重新分配内存空间,从而导致之前的地址无效。
map基本操作
获取元素(判断元素是否存在)
map使用key作为索引获取元素。
value, ok := map1["nihao"]
value := map1["nihao"]
如果存在ok等于true,value等于对应的值,不存在则ok为false,value为对应类型的零值,其中ok可以省略不写。
获取元素个数
map可以使用len函数来获取元素个数,如果map为nil或元素为空时,len等于0。
var map1 map[string]int
fmt.Println(len(map1))
添加修改
如果存在则修改,不存在则添加。
map1["nihao"] = 100
x+=yx++
map1["nihao"] = map1["nihao"] +1
map1["nihao"] ++map1["nihao"] += 1
删除
delete 内置函数用于删除map指定键的元素,如果map为nil或不存在这样的元素,则删除是一个空操作。
delete(map1,"nihao")
遍历
for range
map1 := map[string]int{}
map1["张三"] = 90
map1["小明"] = 100
map1["娜扎"] = 60
for k, v := range map1 {
fmt.Println(k, v)
}
输出:
小明 100
娜扎 60
张三 90
按照顺序进行遍历
map是无序存储的,而且每次遍历的顺序都是随机的,如果想要顺序遍历,可以将key放到切片中,随后对切片进行排序,通过排好序的切片访问map。
map1 := map[string]int{}
map1["张三"] = 90
map1["小明"] = 100
map1["娜扎"] = 60
keySlice := make([]string, 0)
for k := range map1 {
keySlice = append(keySlice, k)
}
sort.Strings(keySlice)
fmt.Println(keySlice)
for _, key := range keySlice {
fmt.Println(key, map1[key])
}
判断两个map是否相等
如同切片一样,map之间是不可以之间比较的,但是可以跟nil比较。如果想要判断两个map是否相等,可以使用循环的方式进行判断。
func equal(x, y map[string]int) bool {
if len(x) != len(y) {
return false
}
for k1, v1 := range x {
if v2, ok2 := y[k1]; !ok2 || v1 != v2 {
return false
}
}
return true
}
利用map实现set
go语言中没有set数据结构,但是我们可以使用map来实现set。
map1 := map[string]bool{}
map1["张三"] = true
map1["小明"] = true
map1["娜扎"] = true
if !map1["nihao"] {
map1["nihao"] = true
}
fmt.Println(map1)
输出:
map[nihao:true 娜扎:true 小明:true 张三:true]
利用辅助函数设置不可比较的key
map中的key是必须能够使用”==“比较的,如果需要存储不能比较的数据,我们可以利用辅助函数将key转化为可以比较的数据。
func TestMap10(t *testing.T) {
a1 := [...]int{1, 2, 3, 4, 5, 6, 7, 8, 9}
s1 := a1[:5]
s2 := a1[:8]
map1 := map[string]bool{
k(s1): false,
k(s2): false,
}
fmt.Println(map1)
}
func k(list []int) string {
return fmt.Sprint(list)
}
输出:
map[[1 2 3 4 5 6 7 8]:false [1 2 3 4 5]:false]