疑问 没有缓存的chan在发送阻塞的时候已经把值存进去了还是在读的时候存的

a312024054 · · 2394 次点击
规范里面对Send statements的说明是: Both the channel and the value expression are evaluated before communication begins 问题的关键在于`communication begins`发生在什么时候? 这里有4个时间点: A:`num++` B:`<-c` C: `c <- *p` D: `*p`这个表达式求值 `communication begins`可能指的时间点是B或C,就是说D可能发生在goroutine里面`time.Sleep(time.Second)`之后,B或C之前的任意时刻 根据Go memory model,有几个happen before是可以确定的: A在B之前,B在C之前 那么就有下面两种情况: 1. 如果D发生在B之前,由于A也在B之前,那么不能确定A和D谁先在前 2. 如果D发生在C之前,由于A也在C之前,那么也不能确定A和D的顺序 在A和D的执行顺序不确定的情况下,同一程序每次执行的结果都可能不同,更不要指望把D里面的`*p`换成`num`后两者执行结果每次都相同 实际应用中也不会有这样用Go用的不彻底的代码:用channel传递一个全局变量,却没有在从channel里面获取到这个变量之后再修改 `Do not communicate by sharing memory; instead, share memory by communicating.`
#23
更多评论
你这个有 data race,结果具有不确定性
#1
<a href="/user/channel" title="@channel">@channel</a> 所以两个的睡眠时间是不一样的呀
#2