映射:键值存储
创建、读取、写入和删除映射条目
映射:键值存储 是 CoddyKit 上的免费 Go Academy 课时。 这是第 3 节课,共 4 节。 你可以在下方免费阅读本课时的完整内容 — 然后在浏览器中使用内置代码编辑器和全天候 AI 导师进行实践。 这是 Go Academy 学习路径的一部分,你的进度在网页和 CoddyKit 应用中同步。 Go Academy 课程共包含 4 节课。
什么是映射?
Go 中的映射是由键值对组成的无序集合。键必须是可比较类型(例如字符串、整数等)。映射是由哈希表提供底层支持的引用类型。
创建映射
使用字面量或 make:
package main
import "fmt"
func main() {
ages := map[string]int{"Alice": 30, "Bob": 25}
cache := make(map[string]string)
fmt.Println(ages, cache)
}读取与写入
使用 m[key] 访问值,并使用 m[key] = value 赋值。读取不存在的键时会返回零值:
package main
import "fmt"
func main() {
m := map[string]int{}
m["hits"] = 10
m["hits"]++
fmt.Println(m["hits"]) // 11
fmt.Println(m["missing"]) // 0
}检查键是否存在
双值形式可以区分不存在的键和零值:
package main
import "fmt"
func main() {
m := map[string]int{"a": 0}
v, ok := m["a"]
fmt.Println(v, ok) // 0 true
v2, ok2 := m["z"]
fmt.Println(v2, ok2) // 0 false
}删除条目
使用内置的 delete 函数。删除不存在的键不会产生任何效果:
package main
import "fmt"
func main() {
m := map[string]int{"x": 1, "y": 2}
delete(m, "x")
delete(m, "z") // no-op
fmt.Println(m) // map[y:2]
}遍历映射
使用 range 进行遍历。顺序不作保证:
package main
import "fmt"
func main() {
scores := map[string]int{"Alice": 90, "Bob": 85}
for name, score := range scores {
fmt.Printf("%s: %d\n", name, score)
}
}值为结构体的映射
映射可以将结构体作为值。请通过临时变量进行更新(映射中的结构体不可寻址):
package main
import "fmt"
type Point struct{ X, Y int }
func main() {
points := map[string]Point{"A": {1, 2}}
p := points["A"]
p.X = 99
points["A"] = p
fmt.Println(points["A"]) // {99 2}
}nil 映射
读取 nil 映射的行为类似于读取空映射(返回零值),但向 nil 映射写入会触发 panic:
package main
func main() {
var m map[string]int
_ = m["key"] // ok — returns 0
// m["key"] = 1 // PANIC: assignment to nil map
}映射不支持并发安全使用
Go 的内置映射不支持协程安全。并发读取没有问题,但并发写入(或同时读取和写入)需要使用互斥锁或 sync.Map:
package main
import "sync"
func main() {
var mu sync.Mutex
m := map[string]int{}
mu.Lock()
m["key"] = 1
mu.Unlock()
_ = m
}统计频次
一种经典的映射模式——统计出现次数:
package main
import "fmt"
func main() {
words := []string{"go", "is", "fast", "go", "is", "go"}
freq := map[string]int{}
for _, w := range words {
freq[w]++
}
fmt.Println(freq) // map[fast:1 go:3 is:2]
}快速检查
读取 Go 映射中不存在的键时会发生什么?
回顾:映射
要点:
- 映射是无序的键值存储
- 使用双值形式检查键是否存在
- 切勿向 nil 映射写入
- 遍历顺序是随机的——如有需要,请先对键排序
- 在并发代码中使用互斥锁保护映射
练习提示
请编写一个函数,接收一个字符串,并返回一个 map[rune]int,用于统计每个字符出现的次数。请使用字符串 "hello" 对其进行测试。
常见问题解答
「映射:键值存储」课时是免费的吗?
是的 — 「映射:键值存储」的完整文本可在网页上免费阅读。要进行交互式练习(内置代码编辑器和全天候 AI 导师)并解锁 Go Academy 课程的其余内容,请升级到 CoddyKit PRO。 Go Academy 课程共包含 4 节课。
「映射:键值存储」这节课中我会学到什么?
创建、读取、写入和删除映射条目 你通过在浏览器中直接运行的动手代码来练习 Go Academy,全天候 AI 导师会在你学习这节课的过程中回答你的问题。
学习 Go Academy 需要有经验吗?
无需任何先前经验。CoddyKit 上的 Go Academy 课程适合初学者到高级学习者,你可以从这里开始或从头开始,按照自己的节奏学习。 这是第 3 节课,共 4 节。
「映射:键值存储」课时需要多长时间?
大多数 CoddyKit 课程大约需要 5–10 分钟。每节课都很精短且互动,所以你能稳步进步,并在网页和应用中从离开的地方继续。
我能在这节 Go Academy 课中编写并运行代码吗?
能。每节 Go Academy 课都包含内置代码编辑器,你可以在浏览器中直接编写并运行真实代码,并获得即时 AI 反馈 — 无需本地设置。
此课程中的所有课时
- 数组:定长集合
- 切片:动态列表
- 映射:键值存储
- 使用 range 遍历集合