マップ
キーで引く入れ物
スライスは番号で引きます。マップはキーで引きます。
Go
counts := map[string]int{
"本": 3,
"家電": 1,
}
counts["本"] // 3map[キーの型]値の型 と書きます。上の例は「文字列で引くと整数が返る」入れ物です。
作り方
Go
counts := map[string]int{} // 空で作る
counts := make(map[string]int) // 同じ意味
var counts map[string]int // これは危険3つ目に注意してください。マップのゼロ値は nil で、書き込むと実行時に止まります。
Go
var counts map[string]int
counts["本"] = 1 // panic: assignment to entry in nil mapスライスは nil でも append できましたが、マップは違います。使う前に必ず作ってください。
読むだけなら nil でも大丈夫、という中途半端さも混乱のもとです。counts := map[string]int{} と書く癖を付けるのが安全です。
読み書き
Go
counts["本"] = 3 // 書く
counts["本"]++ // 増やす
len(counts) // 件数
delete(counts, "本") // 消すcounts["本"]++ が便利です。まだ無いキーでも動きます。
Go
counts := map[string]int{}
counts["本"]++ // 1 になる無いキーを読むとゼロ値の 0 が返るので、0 に 1 を足して 1 になります。集計のコードが、キーの有無を確かめずに書けます。
集計の型
Go
counts := map[string]int{}
for _, category := range categories {
counts[category]++
}この3行が、カテゴリ別の件数を数える定番の形です。第3章では if を並べて数えていたものが、キーの種類が増えても同じ長さで書けます。
順番は保証されない
Go
for k, v := range counts {
fmt.Println(k, v)
}この出力の順番は毎回変わります。Go が意図してばらばらにしています。順番に頼ったコードを書かせないためです。
決まった順で並べたいなら、キーを取り出して並べ替えます。この演習では、順番に頼らない形で答えを組み立ててもらいます。
要件
- マップを使ってカテゴリごとの件数を数える
- マップは
map[string]int{}で作る カテゴリ名はN件ですの形を返す- 1件も無いカテゴリは 0 件として答える
入出力例
countCategory(["本","家電","本"], "本") → "本は2件です"
countCategory(["本","家電","本"], "家電") → "家電は1件です"
countCategory(["本","家電"], "食品") → "食品は0件です"
countCategory(["本","本","本"], "本") → "本は3件です"ヒント
編集 ゆめさく編集部