Ce face map și map-uri
Un map (map[K]V) leagă chei de tip K de valori de tip V: map[string]int leagă texte de numere. Cheia poate fi orice tip comparabil cu == (numere, texte, struct-uri simple, array-uri), dar nu un slice, un map sau o funcție. Map-ul se creează cu un literal sau cu make.
m[k] = v adaugă sau înlocuiește. m[k] dă valoarea, iar pentru o cheie inexistentă dă valoarea zero a tipului. Ca să afli dacă cheia există, folosește forma cu două valori: v, ok := m[k]. delete(m, k) șterge o cheie, len(m) dă numărul de perechi, iar clear(m) le șterge pe toate.
Ordinea parcurgerii cu range este aleatorie. fmt.Println afișează însă un map cu cheile sortate. Un map nu este sigur pentru scrieri din mai multe goroutine fără sync.Mutex. Map-urile sunt referințe: o funcție care primește un map îl poate modifica.
Exemple
Exemplul 1: Operațiile de bază
package main
import "fmt"
func main() {
note := map[string]int{"Ana": 9, "Mihai": 7}
note["Ioana"] = 10 // adăugare
note["Mihai"] = 8 // modificare
fmt.Println(note, "perechi:", len(note))
if n, ok := note["Radu"]; ok {
fmt.Println("Radu are", n)
} else {
fmt.Println("Radu nu are notă; m[\"Radu\"] =", note["Radu"])
}
delete(note, "Ana")
fmt.Println(note)
}
Rezultat
map[Ana:9 Ioana:10 Mihai:8] perechi: 3
Radu nu are notă; m["Radu"] = 0
map[Ioana:10 Mihai:8]
Exemplul 2: Numărarea cuvintelor
frecventa[c]++ merge și pentru cuvinte noi, pentru că pornesc de la 0. Cheile sunt sortate pentru o afișare stabilă.
package main
import (
"fmt"
"maps"
"slices"
"strings"
)
func main() {
text := "ana are mere ana are pere ana"
frecventa := make(map[string]int)
for _, c := range strings.Fields(text) {
frecventa[c]++
}
for _, c := range slices.Sorted(maps.Keys(frecventa)) {
fmt.Printf("%-5s %d\n", c, frecventa[c])
}
}
Rezultat
ana 3
are 2
mere 1
pere 1
Exemplul 3: Map cu valori slice și struct ca cheie
package main
import "fmt"
type Punct struct{ X, Y int }
func main() {
pePrieteni := map[string][]string{}
pePrieteni["Ana"] = append(pePrieteni["Ana"], "Ioana", "Radu")
pePrieteni["Mihai"] = append(pePrieteni["Mihai"], "Ana")
fmt.Println(pePrieteni)
harta := map[Punct]string{{0, 0}: "start", {3, 4}: "comoară"}
fmt.Println(harta[Punct{3, 4}])
}
Rezultat
map[Ana:[Ioana Radu] Mihai:[Ana]]
comoară
Greșeli frecvente
- Scrierea într-un map
nil:panic: assignment to entry in nil map. - Bazarea pe ordinea din
for range: este diferită la fiecare rulare. - Modificarea unui câmp de struct direct în map:
m[k].Nota = 10dăcannot assign to struct field m[k].Nota in map. Citește valoarea, modific-o și pune-o înapoi, sau foloseștemap[K]*T. - Scrieri din mai multe goroutine fără sincronizare:
fatal error: concurrent map writes.
Comenzi înrudite
delete: Șterge o cheie (și valoarea ei) dintr-un map; dacă cheia nu există sau map-ul este nil, nu face nimic.clear: Golește un map (șterge toate cheile) sau pune pe zero toate elementele unui slice, păstrând lungimea.make: Creează și inițializează slice-uri, map-uri și canale, cu lungime, capacitate sau buffer dat.range: Parcurge într-un for elementele unui slice, array, map, text, canal, număr sau iterator.struct și struct-uri: Grupează mai multe câmpuri cu nume și tipuri diferite într-un singur tip; baza pentru modelarea datelor în Go.