【问题标题】:GoRoutine that Returns Two Channels返回两个通道的 GoRoutine
【发布时间】:2019-01-08 03:14:03
【问题描述】:

有人可以帮我理解如何解释函数返回中的以下代码行 - (_, _

我了解该函数返回两个通道。但我不明白它是如何使用以下 (_, _

tee := func(
    done <-chan interface{},
    in <-chan interface{},
) (_, _ <-chan interface{}) {
    out1 := make(chan interface{})
    out2 := make(chan interface{})

    go func() {
        defer close(out1)
        defer close(out2)

        for val := range orDone(done, in) {
            var out1, out2 = out1, out2
            for i := 0; i < 2; i++ {
                select {
                case <-done:
                case out1 <- val:
                    out1 = nil
                case out2 <- val:
                    out2 = nil
                }
            }
        }
    }()
    return out1, out2
}`

【问题讨论】:

  • 没有区别。原作者很“聪明”,以清晰为代价节省了几次击键,这是一个糟糕的权衡。

标签: function go


【解决方案1】:

(_, _ &lt;-chan interface{}) 等价于(&lt;-chan interface{}, &lt;-chan interface{})。除了源代码长度和可读性之外,没有任何区别。

  1. 我们从(&lt;-chan interface{}, &lt;-chan interface{}) 返回值类型开始。
  2. 由于返回值可以有名称,所以可以写(ch1 &lt;-chan interface{}, ch2 &lt;-chan interface{}) 来返回相同的 2 个通道。
  3. 具有相同类型的参数序列(或返回值)可以省略除最后一个变量之外的所有变量的类型。因此我们的返回类型变为:(ch1, ch2 &lt;-chan interface{})
  4. 由于我们并不真正需要返回值的名称,我们可以用下划线替换名称,使它们再次匿名:(_, _ &lt;-chan interface{})

瞧!同一类型的可读通道对。

【讨论】:

    【解决方案2】:

    这是func 声明

    FunctionType   = "func" Signature .
    Signature      = Parameters [ Result ] .
    Result         = Parameters | Type .
    Parameters     = "(" [ ParameterList [ "," ] ] ")" .
    ParameterList  = ParameterDecl { "," ParameterDecl } .
    ParameterDecl  = [ IdentifierList ] [ "..." ] Type .
    

    如您所见,Result 就像方法的参数 Parameters 又归结为 IdentifierList。出现了空白标识符_,它可以替换IdentifierList 中的每个标识符。

    原作者将此与“声明为同一类型的多个标识符”语法一起使用,以产生 - 如前所述 - 一个读起来很奇怪的相同类型的两个返回值的声明。

    https://golang.org/ref/spec#Function_declarations

    您还可以使用空白标识符来实现“删除”参数的功能。当您不需要您实现的接口的参数时,可能会派上用场。

    func foo(a string, _ int, b string) { ... }
    

    第二个参数不可用。

    【讨论】:

      猜你喜欢
      • 2020-08-02
      • 1970-01-01
      • 2012-05-13
      • 1970-01-01
      • 2018-10-23
      • 1970-01-01
      • 2019-04-08
      • 2018-09-29
      • 2013-05-21
      相关资源
      最近更新 更多