为什么 Go 使用通道在 goroutine 之间发送和接收数据而不是使用普通变量?
Why does Go uses channels to send and receive data between goroutines instead of using normal variables?
除了维基百科 https://en.wikipedia.org/wiki/Channel_(programming) 的解释外,我找不到关于这个问题的任何信息。但是我对这个解释并不满意。
渠道解决什么问题?
为什么我们不直接使用普通变量来发送和接收数据呢?
通道解决并发读写问题。基本上,防止一个 goroutine 读取一个变量而另一个 goroutine 写入同一个变量的情况。
另外通道可能有缓冲,所以你可以在锁定前写入多个值。
当然,您不必使用频道。还有其他方法可以在 goroutine 之间发送数据。例如,您可以在为共享变量赋值或从中读取值时使用原子操作,或者在访问它时使用互斥量。
如果您所说的“普通变量”是指,例如,多个 goroutine 写入和读取的切片,那么这是获得数据竞争的保证方式(您不想获得数据竞争)。您可以通过使用某种同步(例如 Mutex 或 RWLock)来避免并发访问。
此时,你
- 重新发明的通道(基本上就是互斥锁下的切片)
- 花费的时间比你需要的多,但你的解决方案仍然很差(没有语法支持,你不能在
select
等中使用你的切片)
除了维基百科 https://en.wikipedia.org/wiki/Channel_(programming) 的解释外,我找不到关于这个问题的任何信息。但是我对这个解释并不满意。
渠道解决什么问题? 为什么我们不直接使用普通变量来发送和接收数据呢?
通道解决并发读写问题。基本上,防止一个 goroutine 读取一个变量而另一个 goroutine 写入同一个变量的情况。
另外通道可能有缓冲,所以你可以在锁定前写入多个值。
当然,您不必使用频道。还有其他方法可以在 goroutine 之间发送数据。例如,您可以在为共享变量赋值或从中读取值时使用原子操作,或者在访问它时使用互斥量。
如果您所说的“普通变量”是指,例如,多个 goroutine 写入和读取的切片,那么这是获得数据竞争的保证方式(您不想获得数据竞争)。您可以通过使用某种同步(例如 Mutex 或 RWLock)来避免并发访问。
此时,你
- 重新发明的通道(基本上就是互斥锁下的切片)
- 花费的时间比你需要的多,但你的解决方案仍然很差(没有语法支持,你不能在
select
等中使用你的切片)