请稍等 ...
×

采纳答案成功!

向帮助你的同学说点啥吧!感谢那些助人为乐的人

关于生成数据被“冲掉”的疑惑

老师好关于数据被冲掉哪里有些疑惑烦请解答

for {
		if hasValue {
			activeWork = w
		} else {
			activeWork = nil
		}
		select {
		case n = <-c1:
			hasValue = true
		case n = <-c2:
			hasValue = true
		case activeWork <- n:
			hasValue = false
		}
	}

以视频中运行结果07为例,work打印0的时候sleep了,这个时候是不是可以说work阻塞了?main函数中的循环从c1和c2拿值,其实这个保证了两个gennerate没有阻塞,但是这个时候,c1或者c2收到值以后hasValue为true,下次循环的时候activeWork不为nil然后会选择到 activeWork <- n,但是这个时候work在sleep,此时程序是怎样一个状态,为什么1-6就会丢弃调,而不是阻塞在哪里等着work的sleep结束以后再打印呢?麻烦您详细解释下

正在回答

2回答

我们看这个worker

func worker(id int, c chan int) {

     for n := range c {

         time.Sleep(time.Second)

         fmt.Printf("Worker %d received %d\n" id, n)

     }

}

注意这个range c就是从channel c收取下一个数据,除非c被 close。worker只有运行到这一行的时候才会从c里面去收数据,在其它行的时候不会。

首先,它从c收了第一个元素0,然后sleep 1秒。而此时generator正在不断的生成数据。main函数里的select中,虽然activeWorker非nil,但是case activeWork <- n:这个分支不会被选中。因为worker运行在sleep这行,而不是 range c这行。由于case n = <-c1:处没有保存n,所以1到6被丢弃了。

1秒后,sleep结束,Printf终于把手里这个0打印出来,也很快也结束。worker运行到range c这行,开始收数据,所以接下来的case activeWork <- n:很有可能被选中,此时这个n已经到了7。

0 回复 有任何疑惑可以回复我~
  • 提问者 Stonebangbang #1
    非常感谢!明白了
    回复 有任何疑惑可以回复我~ 2020-06-03 21:55:38
  • EnzoLiu #2
    简单来说,work卡在了sleep位置等待,而generator那边还在不断产生数据 新产生的数据覆盖了之前的数据,造成了部分数据丢失的问题
    回复 有任何疑惑可以回复我~ 2020-08-01 19:34:50
ccmouse 2020-06-03 16:27:04

抱歉隔了很多天才来回答你这个问题。不知什么原因这里标点符号没有了。还请同学重新编辑一下你的问题,或者编辑一下回复在这里也可以,我再来针对性的看。

0 回复 有任何疑惑可以回复我~
  • 提问者 Stonebangbang #1
    老师好,已经编辑了,您可以看一下.
    不知道算不算bug,中文标点没了
    回复 有任何疑惑可以回复我~ 2020-06-03 17:20:38
  • ccmouse 回复 提问者 Stonebangbang #2
    好的我看到了。回在问题下面。
    回复 有任何疑惑可以回复我~ 2020-06-03 18:02:55
问题已解决,确定采纳
还有疑问,暂不采纳
意见反馈 帮助中心 APP下载
官方微信