V
Vel·ToolKit
Simple · Fast · Ready to use
EN
Chapter 7 of 20

Maps

Declaration, CRUD, iteration, concurrency safety

Declaration and Initialization

package main

import "fmt"

func main() {
    m := map[string]int{
        "alice": 30,
        "bob":   25,
    }

    // using make
    m2 := make(map[string]int)
    m2["x"] = 1

    fmt.Println(m, m2)
}

Read / Write / Delete

package main

import "fmt"

func main() {
    m := map[string]int{"alice": 30, "bob": 25}

    m["alice"] = 31         // write
    v := m["alice"]         // read
    fmt.Println(v)

    if cv, ok := m["carol"]; ok { // check for existence
        fmt.Println("carol:", cv)
    } else {
        fmt.Println("carol missing")
    }

    delete(m, "bob") // delete
    fmt.Println(m)
}

Iteration

range iterates a map in random order; if you need a specific order, sort the keys first.

package main

import (
    "fmt"
    "sort"
)

func main() {
    m := map[string]int{"bob": 1, "alice": 2, "carol": 3}

    keys := make([]string, 0, len(m))
    for k := range m {
        keys = append(keys, k)
    }
    sort.Strings(keys)
    for _, k := range keys {
        fmt.Println(k, m[k])
    }
}

Concurrency Safety

Maps are not concurrency-safe. Concurrent read/write across goroutines needs a lock, or use sync.Map (suited to read-heavy workloads with a relatively stable key set).

package main

import (
    "fmt"
    "sync"
)

func main() {
    var (
        mu sync.Mutex
        m  = map[string]int{}
    )
    set := func(k string, v int) {
        mu.Lock()
        defer mu.Unlock()
        m[k] = v
    }

    var wg sync.WaitGroup
    for i := 0; i < 10; i++ {
        wg.Add(1)
        go func(i int) {
            defer wg.Done()
            set(fmt.Sprintf("k%d", i), i)
        }(i)
    }
    wg.Wait()
    fmt.Println(len(m))
}