多线程-释放锁带来的危险

type KV struct {
    mu Mutex
    data map[string]string
}

func (kv *KV) SendData() {
    for {
        sleep(1s)
        for _, host := hostList {
            go SendDataToRemote() {
                kv.mu.lock()
                // send kv.data['x'] to remote
                kv.mu.unlock()
            }
        }
    }
}

func (kv *KV) DeleteAnElem(k string) {
    kv.mu.lock()
    // delete data[k]
    kv.mu.unlock()
}

func main() {
    kv := make(KV)
    go kv.SendData()
    go kv.DeleteAnElem("x")
}

我想到有三种方案保护kv.data["x"]:

  1. Stop The World方式,每次网络传输时,禁止DeleteAnElem()执行,等所有网络传输结束后,再允许执行DeleteAnElem()。这种方式效率低。
  2. 在网络传输前,将要传输数据打包成参数,传给SendDataToRemote(),然后SendDataToRemote()与DeleteAnElem()互相独立,可以完全并行执行。
  3. SendDataToRemote()与DeleteAnElem()依然争抢kv.data,每次SendDataToRemote()获取锁时,先检查kv.data["x"]是否存在。总结一句话:获得锁之后,首先检查全局变量的状态,以防被其它线程修改
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。