【问题标题】:Why using `chan struct{}` when wait something done not `chan interface{}`?为什么在等待完成而不是 `chan interface{}` 时使用 `chan struct{}`?
【发布时间】:2019-11-27 13:09:55
【问题描述】:

在 golang 中,当我们需要等待某事完成时,我们会使用通道。

示例:

done := make(chan struct{})
go func() {
    // ...
    close(done)
}()
<-done

但是,另一方面,chan interface{} 也适用于这种情况。

那么,chan struct{}chan interface{} 有什么区别?

示例2:

done := make(chan struct{})
go func() {
    // ...
    done <- struct{}{}
}()
<- done

在其他情况下,如果不关闭 goroutine 中的通道而不是发送对象给它。

在goroutine中会创建一个对象,但是如果使用chan interface{},可以将nil对象发送到channel。

使用chan struct{}会更好吗?

【问题讨论】:

    标签: go


    【解决方案1】:

    在您的“完成”通道示例中,从功能上讲,通道实际上可以是任何类型,因为实际上没有发送任何数据,并且通道仅用作信号机制。但考虑到内存利用率,struct{} 是 Go 中可用的最小数据类型,因为它实际上不包含任何内容,因此不需要分配,这就是它通常用于此类场景的原因。

    【讨论】:

      【解决方案2】:

      空结构struct {} 不需要内存。所以如果你有一个大容量的频道,你可以通过从make(chan bool, 1&lt;&lt;16)切换到make(struct {}, 1&lt;&lt;16)来节省几个字节。使用 interface {} 需要更多空间,在这里真的很奇怪。

      对于无缓冲的完成通道,我认为使用 struct {} 是错误,因为它不清楚。使用简单的chan bool 更为明智。使用 interface {} 是完全错误的:它可能会占用更多空间,甚至比 struct {} 更不清晰。

      【讨论】:

      • 我对你的最后一段感到困惑。对于无缓冲的完成通道,struct{} 在什么意义上是错误的?而chan bool 怎么更明智呢? chan bool 暗示您将通过通道发送真值或假值,这不是真的,所以对我来说这似乎是“错误的”。但我很想知道你的推理。
      • @Flimzy Done stdlib 中的通道是 chan bool,即使您从不发送 false 或什至不发送任何内容,只是关闭通道,使用 chan bool 更自然。例如。 chan struct{} 也没有表明您从不打算发送任何东西。而且 strcut {} 更易于输入和阅读,尤其是一种具有特殊语义的罕见语言结构,因为 struct{} 的所有实例都可能共享相同的内存位置。不太常见,更复杂,更多字符,不太清楚 ==> 错误。
      • “标准库中的已完成通道是 chan bool”——这不是一个普遍正确的说法。 stdlib 中有很多关于完成通道的chan struct{} 示例。不过谢谢你的解释。
      猜你喜欢
      • 2013-09-19
      • 1970-01-01
      • 2021-11-16
      • 2019-05-31
      • 2015-08-31
      • 2015-11-02
      • 1970-01-01
      • 2019-06-22
      • 1970-01-01
      相关资源
      最近更新 更多