golang 中map的并发安全

golang 自带的map不是并发安全的,并发读写会报错:

fatal error: concurrent map read and map write

一般的解决方式是加锁,控制互斥。

1.加锁的map

如下代码所示:

package main

import (
    "fmt"
    "sync"
    "time"
)

type Map struct {
    m map[int]int
    sync.RWMutex
}


func(this *Map) Get(key int) int {
    this.RLock()
    defer this.RUnlock()
    
    v := this.m[i]
    return v
}

func(this *Map) Set(k, v int) {
    this.Lock()
    defer this.Unlock()
    
    this.m[k] = v
}

func main(){

    newMap := &Map{m: make(map[int]int)}
    
    for i := 0; i< 10000; i<++ {
        go newMap.Set(i, i)
    }
    
    for i := 0; i< 10000; i<++ {
        go fmt.Println(i, newMap.Get(i))
    }
    
    time.Sleep(time.Second)
}

2.使用sync.Map

从1.9版本开始,sync包中提供了并发安全的map,也就是sync.Map,其内部实现上已经做了互斥处理。

使用举例如下:

例子中,使用Store设置kv,使用Load读取kv,使用Delete删除kv。

package main

import (
        "fmt"
        "sync"
)

type Counter struct {
        count int
}

func main() {
        var m sync.Map

        m.Store("a", 1)
        m.Store("b", 2)

        counter := &Counter{count:2}
        m.Store("c", counter)

        fmt.Println("m:", m)

        v, ok := m.Load("a")
        fmt.Println("a v:", v, ", ok:", ok)
        fmt.Printf("a type: %T\n", v)

        v, ok = m.Load("b")
        fmt.Println("b v:", v, ", ok:", ok)

        v, ok = m.Load("c")
        fmt.Println("c v:", v, ", ok:", ok)
        fmt.Printf("c type %T\n", v)
        vc,_ := v.(*Counter)
        vc.count += 1


        fmt.Println("================")
        v, ok = m.Load("c")
        fmt.Println("c v:", v, ", ok:", ok)

        m.Delete("d")
}

output:

m: {{0 0} {{map[] true}} map[a:0xc00000e028 b:0xc00000e030 c:0xc00000e038] 0}
a v: 1 , ok: true
a type: int
b v: 2 , ok: true
c v: &{2} , ok: true
c type *main.Counter
================
c v: &{3} , ok: true

3.参考

sync.Map

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值