待解决疑问

待解决疑问

  1. 问题一
    sync.map同步锁:

read:
k1-v1 k2-v2 k3-v3

dirty:
k1-123456

如果read的穿透次数一直达不到dirty map的长度, 那么一直不会讲dirty的数据更新到read中,
多线程并发读取的k1一直是旧的数据?

  1. cond相关 wait调用必须加锁
    如果运动员等待的实例代码, wait时去除加锁, 那么会报错:
func main() {
    //创建Cond
    c := sync.NewCond(&sync.Mutex{})

    //声明ready变量
    var ready int

    for i := 0; i < 10; i++ {
       go func(i int) {
          time.Sleep(time.Duration(rand.Int63n(10)) * time.Second)
          // 加锁更改等待条件
          c.L.Lock()
          ready++
          c.L.Unlock()
          log.Printf("运动员#%d 已准备就绪\n", i)

          // 广播唤醒所有的等待者
          c.Broadcast()
       }(i)
    }

    //互斥锁上锁
    //c.L.Lock()
    for ready != 10 { //符合阻塞条件, 就进去阻塞
       c.Wait()
       log.Println("裁判员被唤醒一次")
    }
    //互斥锁解锁
    //c.L.Unlock()

    //所有的运动员是否就绪
    log.Println("所有运动员都准备就绪。比赛开始,3,2,1, ......")
}

出现这个问题的原因在于,
cond.Wait 方法的实现是,把当前调用者加入到 notify 队列之中后会释放锁
(如果不释放锁,其他 Wait 的调用者就没有机会加入到 notify 队列中 了),然后一直等待;

等调用者被唤醒之后,又会去争抢这把锁。如果调用 Wait 之前不加锁的话,就有可能 Unlock 一个未加锁的 Locker。
所以切记,调用 cond.Wait 方法之前一定要加锁。

疑问:
既然队列中有一个UnLock解锁动作, 那么自己代码中的Unlock动作还有必要写吗?

  1. f
  2. f
  3. f
  4. f
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值